鞋盒(box)
鞋盒(Box)
题意
DD 在一个黑暗的房间里,有两个鞋盒:
- 一个盒子装左脚的鞋
- 另一个盒子装右脚的鞋
两个盒子中分别有 n 种不同颜色的鞋子。已知两个盒子中每种颜色鞋子的数量。
现在 DD 希望从两个盒子中分别取出一些鞋子,保证一定能凑出一双颜色相同的鞋子(即左脚和右脚各有一只,且颜色相同)。
从两个盒子中拿出鞋子的数量不要求相等。在所有可能的方案中,找出鞋子总数量最少的方案。
输出这个最少的总数量。
范围
1 ≤ n ≤ 20- 每种颜色的鞋子数量
≤ 10^5 - 总鞋子数量可能很大,需要用
long long
样例
输入
4
0 6 1 6
1 5 0 6
输出
10
思路
要保证一定能凑出一双相同颜色的鞋子,意味着:左右鞋盒中取出的鞋子,在颜色上必须有交集。
也就是,存在至少一种颜色 i,使得左边取了颜色 i 的鞋,右边也取了颜色 i 的鞋。
便可用二进制枚举
得代码
#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int N=20;
int n;
ll a[N],b[N];
ll sum1,sum2;
ll sum=1e18;
ll df[N];
void dfs(int p){
if(p>n){
ll num1=0,num2=0;
ll mi1=1e18,mi2=1e18;
for(int i=1;i<=n;i++){
num1+=a[i]*df[i];
num2+=b[i]*df[i];
if(df[i]) mi1=min(mi1,a[i]);
if(df[i]) mi2=min(mi2,b[i]);
}
if(mi1==1e18||mi2==1e18) return;
sum=min(sum,sum1-num1+1+sum2-mi2+1);
sum=min(sum,sum2-num2+1+sum1-mi1+1);
return;
}
for(int i=0;i<=1;i++){
df[p]=i;
dfs(p+1);
}
}
int main(){
cin >> n;
for(int i=1;i<=n;i++){
cin >> a[i];
sum1+=a[i];
}
for(int i=1;i<=n;i++){
cin >> b[i];
sum2+=b[i];
}
dfs(1);
cout << sum;
return 0;
}

浙公网安备 33010602011771号