- 有时候结合题目条件,求出所有dp值,最后再筛选满足条件的部分
- 分类讨论:A购买3件及以上,A未购买3件以上
- 设 d p [ i ] [ j ] [ k ] dp[i][j][k] dp[i][j][k],处理到第i件商品,A累计已经购买j件(如果j>=3,那么j=3),B当前状态为k件(k = 0,1,2)时价格的最小值
- A购买3件以上:从初始开始转移,只不过最后只取j=3,即
d
p
[
n
]
[
3
]
[
k
]
,
k
∈
0
,
1
,
2
dp[n][3][k],k\in 0,1,2
dp[n][3][k],k∈0,1,2.打7折的处理:转移过程中A的所有价格乘以7,B的所有价格乘以10.
- 条件是到达末尾A的总件数必须>=3
- 最后每个dp的价格除以10
- A未购买3件以上:从初始开始转移即可,相当于忽略A打7折的条件
class Solution {
typedef long long ll;
public:
int goShopping(vector<int>& priceA, vector<int>& priceB) {
array<ll,2> A[priceA.size()];
array<ll,2> B[priceB.size()];
for(ll i = 0;i<priceA.size();i++)
{
A[i][0] = (ll)priceA[i];
A[i][1] = i;
B[i][0] = (ll)priceB[i];
B[i][1] = i;
}
sort(A,A+priceA.size(),[&](array<ll,2> a,array<ll,2> b){return B[a[1]][0] > B[b[1]][0];});
sort(B,B+priceB.size(),[&](array<ll,2> a,array<ll,2> b){return a[0] > b[0];});
ll n = priceA.size();
ll dp[n+1][4][3];
for(ll x = 0;x<4;x++)
for(ll y = 0;y<3;y++)
dp[1][x][y] = INT_MAX;
//第一次转移,乘7除以10
dp[1][1][0]=A[0][0] *7;
dp[1][0][1]=B[0][0] *10;
for(int i = 0;i<n;i++) cout << A[i][0] << endl;
for(int i = 0;i<n;i++) cout << B[i][0] << endl;
for(ll i = 2;i<n+1;i++)
{
dp[i][0][0] = dp[i-1][0][2]; //只能是在B买
dp[i][0][1] = dp[i-1][0][0] + B[i-1][0]*10;
dp[i][0][2] = dp[i-1][0][1] + B[i-1][0]*10;
dp[i][1][0] = min(dp[i-1][0][0] + 7*A[i-1][0],dp[i-1][1][2]); //第i件在B买或在A买
dp[i][1][1] = min(dp[i-1][0][1] + 7*A[i-1][0],dp[i-1][1][0] + 10 * B[i-1][0]);
cout << dp[i][1][1] << endl;
dp[i][1][2] = min(dp[i-1][0][2] + 7*A[i-1][0],dp[i-1][1][1] + 10 * B[i-1][0]);
dp[i][2][0] = min(dp[i-1][1][0] + 7*A[i-1][0],dp[i-1][2][2]); //第i件在B买或在A买
dp[i][2][1] = min(dp[i-1][1][1] + 7*A[i-1][0],dp[i-1][2][0] + 10 * B[i-1][0]);
dp[i][2][2] = min(dp[i-1][1][2] + 7*A[i-1][0],dp[i-1][2][1] + 10 * B[i-1][0]);
dp[i][3][0] = min(dp[i-1][2][0] + 7 * A[i-1][0],min(dp[i-1][3][0] + 7*A[i-1][0],dp[i-1][3][2])); //第i件在B买或在A买
dp[i][3][1] = min(dp[i-1][2][1] + 7 * A[i-1][0],min(dp[i-1][3][1] + 7*A[i-1][0],dp[i-1][3][0] + 10 * B[i-1][0]));
dp[i][3][2] = min(dp[i-1][2][2] + 7 * A[i-1][0],min(dp[i-1][3][2] + 7*A[i-1][0],dp[i-1][3][1] + 10 * B[i-1][0]));
}
ll ans = INT_MAX;
for(ll y = 0;y<3;y++)
{ ans = min(ans,dp[n][3][y]/10);
}
for(ll x = 0;x<4;x++)
for(ll y = 0;y<3;y++)
dp[1][x][y] = INT_MAX;
//第一次转移,乘7除以10
dp[1][1][0]=A[0][0] ;
dp[1][0][1]=B[0][0] ;
for(ll i = 2;i<n+1;i++)
{
dp[i][0][0] = dp[i-1][0][2]; //只能是在B买
dp[i][0][1] = dp[i-1][0][0] + B[i-1][0];
dp[i][0][2] = dp[i-1][0][1] + B[i-1][0];
dp[i][1][0] = min(dp[i-1][0][0] + A[i-1][0],dp[i-1][1][2]); //第i件在B买或在A买
dp[i][1][1] = min(dp[i-1][0][1] + A[i-1][0],dp[i-1][1][0] + B[i-1][0]);
dp[i][1][2] = min(dp[i-1][0][2] + A[i-1][0],dp[i-1][1][1] + B[i-1][0]);
dp[i][2][0] = min(dp[i-1][1][0] + A[i-1][0],dp[i-1][2][2]); //第i件在B买或在A买
dp[i][2][1] = min(dp[i-1][1][1] + A[i-1][0],dp[i-1][2][0] + B[i-1][0]);
dp[i][2][2] = min(dp[i-1][1][2] + A[i-1][0],dp[i-1][2][1] + B[i-1][0]);
dp[i][3][0] = min(dp[i-1][2][0] + A[i-1][0],min(dp[i-1][3][0] + A[i-1][0],dp[i-1][3][2])); //第i件在B买或在A买
dp[i][3][1] = min(dp[i-1][2][1] + A[i-1][0],min(dp[i-1][3][1] + A[i-1][0],dp[i-1][3][0] + B[i-1][0]));
dp[i][3][2] = min(dp[i-1][2][2] + A[i-1][0],min(dp[i-1][3][2] + A[i-1][0],dp[i-1][3][1] + B[i-1][0]));
}
for(ll x = 0;x<3;x++)
{
for(ll y = 0;y<3;y++)
ans = min(ans,dp[n][x][y]);
}
system("pause");
return ans;
}
};
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)