http://acm.hdu.edu.cn/showproblem.php?pid=6501
Problem B. Memory Banks
Time Limit: 8000/4000 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others)
Total Submission(s): 2807 Accepted Submission(s): 458
Problem Description
We have purchased 60 different types of memory banks, typed as 0 to 59, A bank of type i has 2^i memory capacity. We have Xi memory banks of type i.
We also have n workstations numbered from 1 to n. The ith workstation needs exactly (no more and no less) Wi memory capacity to work.
Each workstation can use unlimited amount of memory banks, Total memory capacity of this workstation is the sum of capacity of all memory banks it used.
We need to make all workstations work and calculate the total capacity of unused memory banks, can you help us?
Input
Input is given from Standard Input in the following format:
X0 … X59
n
W1 … Wn
Constraints
0 ≤ Xi ≤ 2^60
1 ≤ n ≤ 100000
0 ≤ Wi ≤ 2^60
All of them are integers.
Output
Print one line denotes the answer.
If it is possible to make all workstations work, output a single number represents the total capacity of unused memory banks. It maybe very large, you should modulo 1000000007(10^9 + 7)
Otherwise output -1
Sample Input
4 2 2 3 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0
3
10 8 16
2 2 2 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0
4
2 4 8 1
Sample Output
6
-1
Source
2018 东北地区大学生程序设计竞赛
Recommend
We have carefully selected several similar problems for you: 6900 6899 6898 6897 6896
思路:每个station用使用若干个bank,The ith workstation needs exactly (no more and no less) Wi memory capacity to work. 意味着必须找到用若干个bank恰好填充每个station的方式,若找不到则返回-1,找到则返回剩余容量。
注意:取模运算时,每一个需要取模的变量都要重新设变量储存取模结果,之后再用新变量进行运算,有以下两个原因。
1.A%mod*B%mod有可能A%mod和B相乘的结果爆long long
2.如果之后样例要用到A,一定不能写成A%=mod; 改变了A的值会影响后续运算。
#include <bits/stdc++.h>
using namespace std;
unsigned long long a[100];
const unsigned long long mod=1000000007;
void init()
{
a[0]=1;
for(int i=1;i<=61;i++)
{
a[i]=a[i-1]*2;
}
}
int main()
{
//cout << "Hello world!" << endl;
init();
unsigned long long X[100];
while(cin>>X[0])
{
for(int i=1;i<=59;i++)
{
cin>>X[i];
}
long long n;
cin>>n;
long long b[100000+1000];
for(int i=0;i<n;i++)
{
cin>>b[i];
}
sort(b,b+n);
int flag=0;
for(int i=n-1;i>=0;i--)
{
for(int j=59;j>=0;j--)
{
/*while(b[i]>=a[j]&&X[j]>0)
{
b[i]-=a[j];
X[j]--;
}*/
long long t=b[i]/a[j];//b是station, a是库存
if(X[j]==0)continue;
if(t>X[j])
{
b[i]-=a[j]*X[j];
X[j]=0;
}
else if(t<=X[j])
{
X[j]-=t;
b[i]-=t*a[j];
}
}
if(b[i]!=0)flag=1;
}
if(flag==1)
{
cout<<"-1"<<endl;
continue;
}
else
{
unsigned long long ans=0;
for(int i=0;i<60;i++)
{
long long u=a[i]%mod,v=X[i]%mod;//这个点,害我们wa22次
ans+=u*v;
ans%=mod;
}
cout<<ans<<endl;
}
}
return 0;
}