Getting started generating function

Write a very good blog link: https://blog.csdn.net/xiaofei_it/article/details/17042651

Generating function normally solve problems similar to the following:

5 to 1 yuan, 2 yuan 4, 3 5 yuan, 15 yuan to get, how many combinations?

In certain cases require the use of at least three $ 1, a $ 2 0 5 yuan.

In certain cases there are numerous provisions 1 yuan, 2 yuan, 5 yuan.

……

In fact, most of the problems generating function can also be used dp / backpack to write, but I feel too weak dp easily mistake a template generating function is easier to understand better.

Next is my mother a few introductory function Topic:

I use here the last mark to optimize the efficiency of the generating function, so that a higher efficiency.

HDU1085

Meaning of the questions: coins in denominations of 2, 5, giving their number. The minimum amount of the composition is not asking much.

Ideas: generating function ran out of money for the program n the number of combinations of the number of species, from the beginning to traverse, the first program number is 0 n is the answer.

Code:

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<algorithm>
 4 #define mem(a, b) memset(a, b, sizeof(a))
 5 using namespace std;
 6 
 7 int val[5], num[5], last, last2;
 8 int temp[8100], ans[8100];
 9 
10 int main()
11 {
12     val[0] = 1, val[1] = 2, val[2] = 5;
13     while(scanf("%d%d%d", &num[0], &num[1], &num[2]) != EOF)
14     {
15         if(num[0] + num[1] + num[2] == 0)
16             break;
17         mem(ans, 0), mem(temp, 0);
18         last = 0, ans[0] = 1;
19         for(int i = 0; i < 3; i ++)
20         {
21             last2 = min(last + val[i] * num[i], 8100);
22             memset(temp, 0, sizeof(int) * (last2 + 1));
23             for(int j = 0; j <= num[i] && j * val[i] <= last2; j ++)
24             {
25                 for(int k = 0; k <= last && k + j * val[i] <= last2; k ++)
26                     temp[k + j * val[i]] += ans[k];
27             }
28             memcpy(ans, temp, sizeof(int) * (last2 + 1));
29             last = last2;
30         }
31         for(int i = 0; i <= 8010; i ++)
32         {
33             if(ans[i] == 0)
34             {
35                 printf("%d\n", i);
36                 break;
37             }
38         }
39     }
40     return 0;
41 }
HDU1085

HDU2079

The meaning of problems: there are k rows, each row having two integers a (1 <= a <= 8), b (1 <= b <= 10), expressed as a class have credits b door. Output an integer representing the number of combinations of n learning credits.

Code:

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<algorithm>
 4 #define mem(a, b) memset(a, b, sizeof(a))
 5 using namespace std;
 6 
 7 int n, k;
 8 int val[10], num[10];
 9 int last, last2, temp[50], ans[50];
10 
11 int main()
12 {
13     int T;
14     scanf("%d", &T);
15     while(T --)
16     {
17         last = 0;
18         mem(temp, 0), mem(ans, 0);
19         ans[0] = 1;
20         scanf("%d%d", &n, &k);
21         for(int i = 0; i < k; i ++)
22             scanf("%d%d", &val[i], &num[i]);
23         for(int i = 0; i < k; i ++)
24         {
25             last2 = min(last + val[i] * num[i], n);
26             memset(temp, 0, sizeof(int) * (last2 + 1));
27             for(int j = 0; j <= num[i] && j * val[i] <= last2; j ++)
28             {
29                 for(int k = 0; k <= last && k + j * val[i] <= last2; k ++)
30                 {
31                     temp[k + j * val[i]] += ans[k];
32                 }
33             }
34             memcpy(ans, temp, sizeof(int) * (last2 + 1));
35             last = last2;
36         }
37         printf("%d\n", ans[n]);
38     }
39     return 0;
40 }
HDU2079

HDU2152

The meaning of problems: n kinds of fruit, the program obtains the number of combinations m of the fruit. But there are number of restrictions, there is an upper limit with the lower limit

Code:

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<algorithm>
 4 #define mem(a, b) memset(a, b, sizeof(a))
 5 using namespace std;
 6 
 7 int n, m, down[110], up[110];
 8 int last, last2;
 9 int ans[110], temp[110];
10 
11 int main()
12 {
13     while(scanf("%d%d", &n, &m) != EOF)
14     {
15         for(int i = 0; i < n; i ++)
16             scanf("%d%d", &down[i], &up[i]);
17         mem(temp, 0), mem(ans, 0);
18         ans[0] = 1, last = 0;
19         for(int i = 0; i < n; i ++)
20         {
21             last2 = min(last + up[i], m);
22             memset(temp, 0, sizeof(int) * (last2 + 1));
23             for(int j = down[i]; j <= up[i] && j <= last2; j ++)
24             {
25                 for(int k = 0; k <= last && k + j <= last2; k ++)
26                 {
27                     temp[k + j] += ans[k];
28                 }
29             }
30             memcpy(ans, temp, sizeof(int) * (last2 + 1));
31             last = last2;
32         }
33         printf("%d\n", ans[m]);
34     }
35     return 0;
36 }
HDU2152

template:

. 1 ANS [ 0 ] = . 1 , Last = 0 ;   // initialize the plurality of sets of input words also MEM (ANS, 0), MEM (TEMP, 0) 
2  for ( int I = 0 ; I <K; I ++ )
 . 3  {
 . 4      last2 = min (last Val + [I] * NUM [I], n-); // time of the last calculation 
. 5      Memset (TEMP, 0 , the sizeof ( int ) * (+ last2 . 1 )); // only empty TEMP [0 ... last2] 
. 6      for ( int J = Down [I]; J <= up [I] && * J Val [I] <= last2; J ++) //Note that each of a number of factors traversing the upper and lower limits 
. 7      {
 . 8          for ( int K = 0 ; K <= J + K * Last && Val [I] <= last2; K ++) // iterate answer array update answer, before factor multiplication factor obtained by multiplying the provisional answer 
. 9          { // ANS is the last in the last, temp is in last2 
10              TEMP [Val * K + J [I]] = + ANS [K];
 . 11          }
 12 is      }
 13 is      the memcpy (ans, TEMP, the sizeof ( int ) * (+ last2 . 1 )); // TEMP assigned to a temporary answer to be updated ans 
14      Last = last2; // update Last 
15 }

 

Guess you like

Origin www.cnblogs.com/yuanweidao/p/11233803.html