#include
bool isValidPassword(int password) {
return 1000 <= password && password <= 9999;
}
int main() {
for (int A = 1; A <= 9; ++A) {
for (int B = 1; B <= 9; ++B) {
for (int C = 1; C <= 9; ++C) {
int D = 16 - A - B - C; // 计算D的值
if (D >= 1 && D <= 9 && A != B && A != C && A != D && B != C && B != D && C != D) {
// 计算密码
int password = 1000 * (A - 1) + 100 * (B - 2) + 10 * (C - 3) + (D - 4);
// 如果密码是四位数,则输出
if (isValidPassword(password)) {
std::cout << "数字组合: (" << A << ", " << B << ", " << C << ", " << D << "), 密码: " << password << std::endl;
}
}
}
}
}
return 0;
}
下面鄙人分享解答“deepin论坛打卡赛“的一些思路,其中不免存在些许问题,望见谅。
题一
首先构建密码图形:
统计数字出现次数:
由题设可知:由于位置都不对,所以每个数字出现的次数小于 4。排除 3 和 5 这两个数字。通过最后四行可知,必然有:1、8、2 、7这四个数字。由此我们得到密码准确数字,现在考虑密码的顺序。
有题设知,密码的位置都不正确,所以可以利用反证法确定某些数字位置。
可以看到 8 和 1 的次数均出现 3 次,那么可以精确确定其位置:
同时也可以确定 7 的位置,因为 8 已经占据首位,所以 7 必定位于第二位,由此得到最终答案:
题二
由于每分钟增加 1 倍,可以简单的构建该模型函数 N=2^{n}\quad n\in(1,2,3,...,12) ,
由于 12 分钟后篮子满了,那么可以得到:
现在找出半篮子鸡蛋的时间,即 C/2 个鸡蛋的时间,
所以,在第 11 分钟时为半篮子鸡蛋。
题三
至少有 3 个红球的概率可以通过反证法考虑:恰好有 3 个红球、恰好有 4 个红球、恰好有 5 个红球的概率和。设 P 为至少有 3 个红球的概率,那么可得
所以至少有 3 个红球的概率为 \frac{1}{2} 。
题四
事实上,本题可以看作是一个排列问题。
由题设可知每人拿到的是随机不同的数字卡片,那么我们假设相邻二者两两交换,即
那么仅需 5 次即可让每个人拿到与自己编号相同的卡片。现在尝试去寻找交换次数小于 5 次的卡片排列方式。
但是这显然是不可能的,每人仅能和左右相邻交换卡片,所以必然需要花费 5 次及以上。
题四(改)
由题设可以使用一个简单的程序得到结果。
下面我给出具体 C++代码:
具体结果为:
简化输出方式为得到的全部结果为:
对该题目,鄙人存在以下疑惑:
题五
答案为 6765,使用动态规划而非递归求解。
原因在于:斐波那契数列的增长速度非常快,第 20 项就已经超过 int 类型范围,同时由于递归调用的深度和计算量都非常大,频繁调用较大数字(哪怕仅有 20 项),使用动态规划或者矩阵连乘等算法都更为优秀。
下面是使用动态规划的 C++代码: