1042: [HAOI2008] coin shopping time limit:10 Sec Memory limit:162 MB
submit:1380 solved:814
[Submit] [Status] [Discuss] Description
Coin shopping A total of 4 kinds of coins. The denominations were c1,c2,c3,c4. Someone went to the store to buy something and went to tot. Each time with a di ci coin, buy something of Si value. How many methods of payment do you have each time?
Input
The first line C1,c2,c3,c4,tot under the Tot line d1,d2,d3,d4,s
Output
Number of methods per time
Sample Input1 2 5) 10 2
3 2 3) 1 10
2 2 2Sample Output4
-HINT
Data size
di,s<=100000
tot<=1000
Source
has been the wrong to scare the urine ...
Magic.. The principle of tolerance and repulsion.
The following is @
The original knapsack problem also has this solution, dynamic programming + the principle of tolerance. With a tot ask, if you do a multiple knapsack problem for each query individually, it will time out. There is a one-time preprocessing, each asking only O (1) The Magic Solution: the principle of tolerance.
F[i] To obtain the scheme number of face value I, without regard to the limit of the quantity of each coin. The state transition equation is
F[i]=sum{f[i-c[k]] | i-c[k]>=0 and k=1..4}
In order to avoid the repetition of the scheme, recursion with K as phase and boundary condition is f[0]=1, so the time complexity of preprocessing is O (S).
Next to each inquiry, the wonderful solution is as follows: according to the principle of repulsion, the answer is to get the face value of the more than the limit of the scheme number-the 1th kind of coin exceeds the limit of the number of programs-the 2nd coin exceeds the limit of the number of schemes-the 3rd type of coin exceeds the limit of the scheme number-4th type of Limit number of Scenarios + 1th, 3 coins at the same time exceed the limit of the number of programs + ... + 1,2,3,4 coins all at the same time exceed the limit of the number of programs.
When the 1th type of coin exceeds the limit, as long as the d[1]+1 coin is used, the remaining coins can be allocated arbitrarily, so the scheme number is f[S-(d[1]+1)c[1]], when and only if (S-(d[1]+1)c[1]) >=0, otherwise the scheme number is 0. The rest of the situation is similar, asking only 16 times per query, so the time to ask for the complexity is O (1).
#include <iostream>#include<cstdio>#include<cstring>#include<cstdlib>#include<algorithm>#include<cmath>#include<vector>using namespacestd;intc[5],tot,s,d[5];Long Longans,f[100001];voidDfsintXintKLong Longsum) { if(sum<0)return; if(x==5) { if(k&1) Ans-=f[sum];Elseans+=F[sum]; return; } DFS (x+1, K +1, sum-(d[x]+1)*c[x]); DFS (x+1, k,sum);}intMain () {scanf ("%d%d%d%d%d", &c[1],&c[2],&c[3],&c[4],&tot); f[0]=1; for(intI=1; i<=4; i++) for(intj=c[i];j<=100000; j + +) F[j]+=f[j-C[i]]; for(intI=tot;i>0; i--) {scanf ("%d%d%d%d%d", &d[1],&d[2],&d[3],&d[4],&s); Ans=0; DFS (1,0, s); printf ("%lld\n", ans); } return 0;}
[HAOI2008] [BZOJ1042] Coin Shopping