Codeforces Round #583 (Div. 1 + Div. 2)A. Optimal Currency Exchange (dfs)

https://codeforces.com/contest/1214/problem/A

安德鲁剩n卢布,想换成欧元和美钞。一美元的价格是d卢布,一欧元需要e卢布。

存在以下美元钞票:1、2、5、10、20、50、100,以及以下欧元钞票— 5、10、20、50、100、200。安德鲁可以购买任何组合的钞票(也可以同一种钞票换取很多),他的目标是将兑换后他将拥有的卢布总数最小化。

给定整数n、e和d,找出安德鲁在购买美元和欧元钞票后能得到的最小卢布数。
input
100
60
70
output
40
input
410
55
70
output
5
input
600
60
70
output
0

误打误撞看漏了一个条件,以为是dfs
虽然wa了之后才发现写假了,但是也是很开心哇
终于会dfs了,is good!

//#include<bits/stdc++.h>
#include<iostream>
#include<cmath>
#include<algorithm>
#include<cstring>
#include<cstdlib>
#include<string>
#include<cstdio>
#include<map>
#include<vector>
#include<set>
#include<queue>
#include<deque>
using namespace std;
typedef long long LL;
typedef pair<int,int> PII;
const int N=500200;
const int M=5002;
const int mod=998244353;
LL a[N],b[N];
//int h[N],w[N],e[N],ne[N],dist[N],idx;
int f[M][M];
bool vis[N],st[N];
int dx[]={-1,0,0,1,-1,-1,1,1},dy[]={0,1,-1,0,1,-1,-1,1};
LL minn=0,maxn=0;
int n,d,e;
void dfs(LL sum,LL idx)
{
    if(idx==14)
    {
        if(sum<=n&&sum>=0) maxn=max(maxn,sum);
        return ;
    }
    if(sum>n) return ;
    dfs(sum+a[idx],idx+1);
    dfs(sum,idx+1);
}
int main()
{
    //cin.tie(0); cout.tie(0); ios::sync_with_stdio(false);
    int T=1;
    //cin>>T;
    while(T--)
    {
        map<int,int> mp;
        mp[1]=1; mp[2]=2; mp[3]=5; mp[4]=10; mp[5]=20; mp[6]=50; mp[7]=100;
        mp[8]=5; mp[9]=10; mp[10]=20; mp[11]=50; mp[12]=100; mp[13]=200;
        cin>>n>>d>>e;
        for(int i=1;i<=7;i++)
        {
            a[i]=mp[i]*d;
            minn+=a[i];
        }
        for(int i=8;i<=13;i++)
        {
            a[i]=mp[i]*e;
            minn+=a[i];
        }
        sort(a+1,a+1+13);
        //for(int i=1;i<=13;i++) cout<<a[i]<<" ";
        dfs(0,1);
        cout<<n-maxn<<endl;
    }
    return 0;
}

此题正解
如下所示

//#include<bits/stdc++.h>
#include<iostream>
#include<cmath>
#include<algorithm>
#include<cstring>
#include<cstdlib>
#include<string>
#include<cstdio>
#include<map>
#include<vector>
#include<set>
#include<queue>
#include<deque>
using namespace std;
typedef long long LL;
typedef pair<int,int> PII;
const int N=500200;
const int M=5002;
const int mod=998244353;
LL a[N],b[N];
//int h[N],w[N],e[N],ne[N],dist[N],idx;
int f[M][M];
bool vis[N],st[N];
int dx[]={-1,0,0,1,-1,-1,1,1},dy[]={0,1,-1,0,1,-1,-1,1};
LL minn=0,maxn=0;
int n,d,e;
int main()
{
    cin.tie(0); cout.tie(0); ios::sync_with_stdio(false);
    int T=1;
    //cin>>T;
    while(T--)
    {
        cin>>n>>d>>e;
        int minn=n%d;
        //cout<<minn<<endl;
        //因为有一张是1块钱的,所以可以初步认定最小的就是n换1之后换不了的美元
        //美元后面的都是1的倍数,所以只用上第一个其实就可以了
        for(int i=0;;i++)
        {
            if(n>=0)
            {
                //1, 2, 5, 10, 20, 50, 100
                minn=min(minn,n%d);
                //5 ,10, 20, 50, 100, 200
                //欧元都是5的倍数,所以只需要判断能否凑出x个d以及y*5个e==n就行了
                n-=e*5;
            }
            else break;
        }
        cout<<minn<<endl;
    }
    return 0;
}
posted @ 2022-07-29 10:40  高尔赛凡尔娟  阅读(16)  评论(0编辑  收藏  举报