zoukankan      html  css  js  c++  java
  • POJ3181--Dollar Dayz(动态规划)

    Farmer John goes to Dollar Days at The Cow Store and discovers an unlimited number of tools on sale. During his first visit, the tools are selling variously for $1, $2, and $3. Farmer John has exactly $5 to spend. He can buy 5 tools at $1 each or 1 tool at $3 and an additional 1 tool at $2. Of course, there are other combinations for a total of 5 different ways FJ can spend all his money on tools. Here they are: 

            1 @ US$3 + 1 @ US$2
    
    1 @ US$3 + 2 @ US$1
    1 @ US$2 + 3 @ US$1
    2 @ US$2 + 1 @ US$1
    5 @ US$1
    Write a program than will compute the number of ways FJ can spend N dollars (1 <= N <= 1000) at The Cow Store for tools on sale with a cost of $1..$K (1 <= K <= 100).

    Input

    A single line with two space-separated integers: N and K.

    Output

    A single line with a single integer that is the number of unique ways FJ can spend his money.

    Sample Input

    5 3

    Sample Output

    5


    完全背包+高精度数

    没有优化直接wa,是数值范围太小
    #include<iostream>
    using namespace std;
    int dp[105][1005];
    int main(){
        int n,k;
        cin>>n>>k;
        dp[0][0]=1;
        for(int i=1;i<=k;i++){
            for(int j=0;j<=n;j++){
                for(int k=0;k*i<=j;k++){
                    dp[i][j]+=dp[i-1][j-k*i];
                }
            }
        }
        cout<<dp[k][n];
        return 0;
    } 

     改用unsigned long long还是wa。那就用两个unsigned long long一个存低位一个存高位。unsigned long long的范围是1844674407370955161,所以用一个比它小一个数量级的数,

    100000000000000000。
    #include<iostream>
    using namespace std;
    unsigned long long dp[105][1005][2];
    #define LIMIT_ULL 100000000000000000
    int main(){
        int n,k;
        cin>>n>>k;
        dp[0][0][1]=1;//低位
        for(int i=1;i<=k;i++){
            for(int j=0;j<=n;j++){
                for(int k=0;k*i<=j;k++){
                    dp[i][j][1]+=dp[i-1][j-k*i][1];
                    dp[i][j][0]+=dp[i-1][j-k*i][0];
                    dp[i][j][0]+=dp[i][j][1]/LIMIT_ULL;//低位的进位加到高位
                    dp[i][j][1]=dp[i][j][1]%LIMIT_ULL;//低位去除进位
                }
            }
        }
        if(dp[k][n][0]){
            cout<<dp[k][n][0];
        }
        cout<<dp[k][n][1];
        return 0;
    } 

    以上比你不是最优的,可能会TLE

    dp[i][j]+=dp[i-1][j-i*k]可以优化成dp[i][j]=dp[i-1][j]+dp[i-1][j-k]

    因为当k>1时的计算结果,已经保存在了dp[i-1][j-k]

    #include<iostream>
    using namespace std;
    unsigned long long dp[105][1005][2];
    #define LIMIT_ULL 100000000000000000
    int main(){
        int n,k;
        cin>>n>>k;
        dp[0][0][1]=1;
        for(int i=1;i<=k;i++){
            for(int j=0;j<=n;j++){
                if(j<i){
                    dp[i][j][1]=dp[i-1][j][1];
                    dp[i][j][0]=dp[i-1][j][0];
                }
                else{
                    dp[i][j][1]=dp[i-1][j][1]+dp[i][j-i][1];
                    dp[i][j][0]=dp[i-1][j][0]+dp[i][j-i][0];
                    dp[i][j][0]+=dp[i][j][1]/LIMIT_ULL;
                    dp[i][j][1]=dp[i][j][1]%LIMIT_ULL;
                }
            }
        }
        if(dp[k][n][0]){
            cout<<dp[k][n][0];
        }
        cout<<dp[k][n][1];
        return 0;
    } 
  • 相关阅读:
    [置顶] java得到前一个月的年月日时分秒
    Windows 8.1 Preview的新功能和新API
    oracle保证读一致性原理
    10161
    Qt国际化
    使用Maven管理依赖JAR文件,自定义项目布局,利用ANT生成不同的发布包
    Haxe2.10到Haxe3,NME到OpenFL的迁移备忘
    设置RichEdit相关颜色说明
    使用MFC CImage类绘制PNG图片时遇到的问题
    把网球计分招式重构到状态模式
  • 原文地址:https://www.cnblogs.com/albert67/p/10323190.html
Copyright © 2011-2022 走看看