链接:登录—专业IT笔试面试备考平台_牛客网
来源:牛客网
题目描述
小w想和你van纸牌
小w有两张纸牌,两张纸牌上都有相同的正整数n
每一轮一张纸牌上的数都可以减去小于等于另外一张纸牌上的数的数
每一轮只能操作和上轮不同的纸牌
小w想知道三轮之后两纸牌上数字之和的最小值
注意,不能减为负数
输入描述:
第一行1个正整数n。
输出描述:
一行一个整数 表示三轮之后两纸牌上数字和的最小值
示例1
输入
复制2
2
输出
复制1
1
说明
样例解释:两张ab上数字分别为2,第一轮,a张减去1(1 <= (b = 2)) 第二轮b减去1(1 <= (a = 1)) ,第三轮a减去1(1 <= (b = 1)),游戏结束a+b = 1,该结果为最可行优解之一
备注:
保证1 ≤ n ≤ 1000000000
分析
推导:
// n n 起始纸牌上相同的整数n
// n-x n 设第一轮减去x
// n-x n-y 设第二轮减去y
// n-x-(n-y) n-y 第三轮,既然要尽量小,所以减去对方(减去小于等于另外一张纸牌上的数的数)
n-x-(n-y) = y-x,当x=y时,y-x取最小值0(题目要求:注意,不能减为负数)
此时将上述推导中的y全部代换为x得
// n n 起始纸牌上相同的整数n
// n-x n 第一轮减去x
// n-x n-x 第二轮减去x
// 0 n-x 第三轮,既然要尽量小,所以减去对方(减去小于等于另外一张纸牌上的数的数)
三轮之后两纸牌上数字之和为n-x
要使n-x最小,显然x要尽量大,又由第二轮右边减去x得知x<=n-x(题目要求:减去小于等于另外一张纸牌上的数的数),化简为x<=2/n,因此x最大取值2/n (至于为什么要通过第二轮来列不等式,因为要尽量缩小x的取值,在第一轮左边减去x,这一步只能粗略判断出x<=n,这个范围虽然正确但很模糊,不够精确)
因此前两轮应减去初始值的一半,第三轮减去对方,这样操作,能使三轮后两纸牌的数字和最小!
完整代码
#include<stdio.h>
int main()
{
int n;
scanf("%d", &n);//本题最大范围是10亿,没有超过21亿左右的int
int a = n, b = n;
a = a - n / 2;//第一轮减初始值一半
b = b - n / 2;//第二轮减初始值一半
a = a - b;//第三轮减去对方
printf("%d", a + b);
return 0;
}