zoukankan      html  css  js  c++  java
  • Educational Codeforces Round 26 D

    Round Subset

    题意:给n个数,从中选出k个数,求选出的k个数的乘积结尾的0最多是多少

    思路:类似于背包的递推,dp[i][j][k]表示前i个数选j个数含有k个5的方案下2的最大数,第一维用滚动数组优化,由于5^26>1e18,所以第二维开200*26即可 递推式为

    dp[i+1][j+1][k+count5[i+1]] = max( dp[ i ] [ j ] [ k ] + count2[ i+1 ], dp[ i+1 ]  [ j+1 ] [ k + count5[ i+1 ] ] );

    dp[ i+1 ] [ j ] [ k ] = max( dp[ i ] [ j ] [ k ], dp[ i+1 ] [ j ] [ k ] );

    dp初始化为-inf,dp[0][0][0]初始化为0

    AC代码:

    #include "iostream"
    #include "iomanip"
    #include "string.h"
    #include "stack"
    #include "queue"
    #include "string"
    #include "vector"
    #include "set"
    #include "map"
    #include "algorithm"
    #include "stdio.h"
    #include "math.h"
    #pragma comment(linker, "/STACK:102400000,102400000")
    #define bug(x) cout<<x<<" "<<"UUUUU"<<endl;
    #define mem(a,x) memset(a,x,sizeof(a))
    #define step(x) fixed<< setprecision(x)<<
    #define mp(x,y) make_pair(x,y)
    #define pb(x) push_back(x)
    #define ll long long
    #define endl ("
    ")
    #define ft first
    #define sd second
    #define lrt (rt<<1)
    #define rrt (rt<<1|1)
    using namespace std;
    const long long INF = 1e18+1LL;
    const int inf = 1e9+1e8;
    const int N=1e5+100;
    const ll mod=1e9+7;
    
    ///dp[i][j][k]表示前i个数选j个数含有k个5的方案下2的最大数
    ll a[205],b[205],c[205],n,k,dp[3][205][205*26];
    int main(){
        ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
        cin>>n>>k;
        for(int i=1; i<=n; ++i){
            cin>>a[i];
            for(ll x=a[i]; x%2==0; x/=2,b[i]++);
            for(ll x=a[i]; x%5==0; x/=5,c[i]++);
        }
        mem(dp,-127); dp[0][0][0]=0;
        int cur=0;
        for(int i=0; i<n; ++i){
            for(int j=0; j<=k; ++j){
                for(int t=0; t<=200*26; ++t){
                    dp[cur^1][j+1][t+c[i+1]]=max(dp[cur^1][j+1][t+c[i+1]],dp[cur][j][t]+b[i+1]);
                    dp[cur^1][j][t]=max(dp[cur^1][j][t],dp[cur][j][t]);
                }
            }
            cur^=1;
        }
        ll ans=0;
        for(ll i=1; i<=200*26; ++i) ans=max(ans,min(i,dp[cur][k][i]));
        cout<<ans;
        return 0;
    }
  • 相关阅读:
    Smarty学习笔记(二)
    Smarty学习笔记(一)
    MVC学习笔记(一)
    2015羊年主流手机配置什么样?
    FPGA学习笔记(一)Verilog语法基础
    FPGA学习笔记(二)模块建立及变量连接
    STM32学习笔记(一)时钟和定时器
    Win8 HTML5与JS编程学习笔记(一)
    Win8 HTML5与JS编程学习笔记(二)
    LUOGU P2831 愤怒的小鸟 (NOIP 2016)
  • 原文地址:https://www.cnblogs.com/max88888888/p/7365150.html
Copyright © 2011-2022 走看看