版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/baidu_36797646/article/details/82841146
题解:
首先显然是把砝码从小到大装进容器中,那么如果我们能够快速知道每次能否再放入砝码,问题就迎刃而解了。题目有个重要条件:他们的中总有一个的重量是另外一个的整数倍,所以我们可以把每个容器用类似进制转换的方法表示,最高位的数字表示能装最大的砝码几个,次高位表示尽量多的装完最大砝码,次大砝码能装的个数……以此类推,把所有容器的数加起来,然后每次装入砝码,相当于在某个位上 ,贪心就行了。
代码:
#include<bits/stdc++.h>
using namespace std;
#define LL long long
#define pa pair<int,int>
const int Maxn=100010;
const int inf=2147483647;
int read()
{
int x=0,f=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
while(ch>='0'&&ch<='9')x=(x<<3)+(x<<1)+(ch^48),ch=getchar();
return x*f;
}
int n,m,a[Maxn],b[Maxn],c[40],d[40],e[Maxn],l=0;
bool check(int p)
{
d[e[p]]--;
int t=e[p];
while(d[t]<0)
{
if(t==l)return false;
d[t]+=c[t+1]/c[t];d[t+1]--;
t++;
}
return true;
}
int main()
{
n=read(),m=read();
for(int i=1;i<=n;i++)a[i]=read();
for(int i=1;i<=m;i++)b[i]=read();
sort(b+1,b+1+m);
int last=0;
for(int i=1;i<=m;i++)
{
if(b[i]==last){e[i]=l;continue;}
c[++l]=last=b[i];e[i]=l;
}
for(int i=1;i<=n;i++)
{
int t=a[i];
for(int j=l;j;j--)
if(t>=b[j])d[j]+=t/c[j],t%=c[j];
}
int ans=0;
for(int i=1;i<=m;i++)
{
if(check(i))ans++;
else break;
}
printf("%d",ans);
}