2019 2.15模拟赛
分裂
【问题描述】
你有一个大小为????的????????????????????,每次你可以从你已有的????????????????????中选择一 个大小不为1的????????????????????,设他的大小为????,然后把它分裂成????和???? − ????,其 中1 ≤ ???? < ????,这样你获得的收益是???? * (???? − ????) 给定????,????,求最少分裂几次才能得到至少????的收益
【输入格式】
从文件 split.in 中读入数据。 第一行两个正整数????,????
【输出格式】
输出到文件 split.out 中。 输出一个非负整数表示答案 如果无法达到????的收益输出−1
【样例输入】
765 271828
【样例输出】
14
【数据规模】
对于30%的数据,有???? ≤ 10
对于100%的数据,有2 ≤ ???? ≤ 1000,1 ≤ ???? ≤ 109
sol:首先对于30%的数据,各种乱搞都可以做。但我写了个dp,dp[i][j]表示大小为 i 的Jabby,切 j 刀可得的最大权值,事实可以过到200,但没有这档分。标算是这么想的:因为要把一个物体切成 j 个,肯定是尽量平均的最优,就枚举 j,然后模拟切得过程,n2水过,其实是可以n*logn的,j显然是可以二分的
inline void Solve_30pts() { int i,j,k,l; dp[1][0]=0; for(i=2;i<=S;i++) { dp[i][0]=0; for(j=1;j<=i/2;j++) { for(k=0;k<=j;k++) { for(l=0;l<=i-j;l++) dp[i][k+l+1]=max(dp[i][k+l+1],dp[j][k]+dp[i-j][l]+j*(i-j)); } } } for(i=0;i<=S;i++) { if(dp[S][i]>=M) { Wl(i); return; } } }