POJ2229 Sumsets 基礎DP

                        Sumsets
Time Limit: 2000MS   Memory Limit: 200000K
Total Submissions: 14344   Accepted: 5709

Description

Farmer John commanded his cows to search for different sets of numbers that sum to a given number. The cows use only numbers that are an integer power of 2. Here are the possible sets of numbers that sum to 7: 

1) 1+1+1+1+1+1+1 
2) 1+1+1+1+1+2 
3) 1+1+1+2+2 
4) 1+1+1+4 
5) 1+2+2+2 
6) 1+2+4 

Help FJ count all possible representations for a given integer N (1 <= N <= 1,000,000). 

Input

A single line with a single integer, N.

Output

The number of ways to represent N as the indicated sum. Due to the potential huge size of this number, print only last 9 digits (in base 10 representation).

Sample Input

7

Sample Output

6

Source

 
 
 
 
題意:給出一個數N,N可以表示成2的冪的和,問有多少種方式。
輸出方式模1000000000。
 
看到題:首先想到的就是必須打表。
剛開始想著推出公式,推不出來。
然後想用DP
 
把1~12這12個數的方式都寫出來了,然後就找到了代碼中的規律。
一想,還真是很有道理。
 
令dp[i]表示數i可以表示的方式。
 
然後對於一個數N,
若N是奇數,就相當於在N-1的所有方式中,每一種方式加上一個1,(湊不了2),所以=dp[N-1]
若N是偶數,就相當於在N-2中每一種有1的方式加上一個1,然後剩下的沒有1的方式,再加1.
有多少方式是沒有包含1的呢?把沒有一個的方式的每一個數除以2,就得到了dp[n/2],所以有這麼多種。
那為什麼不把這個1和其他的1合在一起湊成2呢?
舉例說明:1 1 1和1 2,你把1 1 1 變成1 1 2 和在1 2 加1變成1 1 2是重複的。
 
 
POJ2229 Sumsets 基礎DP
 1 #include<cstdio>

 2 #include<cstring>

 3 #include<algorithm>

 4 

 5 using namespace std;

 6 

 7 const int maxn=1000000+3;

 8 

 9 #define LL long long

10 

11 LL dp[maxn];

12 const LL mod=1000000000;

13 

14 int main()

15 {

16     dp[0]=dp[1]=1;

17     for(int i=2;i<maxn;i++)

18     {

19         if(i%2)

20             dp[i]=dp[i-1];

21         else

22             dp[i]=dp[i-2]+dp[i/2];

23         while(dp[i]>=mod)

24             dp[i]-=mod;

25     }

26 

27     int N;

28     while(~scanf("%d",&N))

29     {

30         printf("%d\n",dp[N]);

31     }

32 

33     return 0;

34 }
View Code

 

 

 

 

 
 
 
 
 
 
 

你可能感兴趣的:(set)