学习C++从娃娃抓起!记录下USACO(美国信息学奥赛)备考学习过程中的题目,记录每一个瞬间。
附上汇总贴:USACO备考冲刺必刷题 | 汇总-CSDN博客
【题目描述】
下面是一个乘法竖式,如果用我们给定的那 n 个数字来取代 *,可以使式子成立的话,我们就叫这个式子为牛式。
***
x **
----------
***
***
----------
****
数字只能取代 *,当然第一位不能为 0,况且给定的数字里不包括 0。
注意一下在美国的学校中教的“部分乘积”,第一部分乘积是第二个数的个位和第一个数的积,第二部分乘积是第二个数的十位和第一个数的乘积。
请计算出牛式的数量。
【输入】
第一行一个正整数 n,表示可用的数集。 第二行 n 个正整数 ai,表示可用的数。
【输出】
输出一行一个整数,表示牛式的总数。
【输入样例】
5
2 3 4 6 8
【输出样例】
1
【代码详解】
#include <bits/stdc++.h>
using namespace std;
int n, t, ans=0;
int a[15];
bool check (int x, int k) // 定义判断数位的函数
{
if (x>=pow(10, k)) return false; // 如果这个数x大于等于10^k,则返回false
while (x>0) { // 使用数位拆分
if (a[x%10] == 0) return false; // 依次判断每个数都在n个数字中,如果不在的话直接返回false
x = x / 10; // 数位拆分
}
return true; // 如果没有不满足的话,那就返回true
}
int main()
{
cin >> n; // 输入n
for (int i=1; i<=n; i++) { // 遍历n个数
cin >> t; // 输入每个数
a[t]=1; // 并使用桶排序方法存到桶中,后面需要判断该数字是否有
}
for (int i=111; i<=999; i++) { // 遍历所有的三位数
for (int j=11; j<=99; j++) { // 遍历所有的二位数
if (check(i, 3) && check(j, 2) && check(i * (j%10), 3) && check(i * (j/10), 3) && check (i*j, 4)) { // 根据题目要求,判断两个数是否为一个为3位数,一个为2位数,3位数乘上2个位的个位和十位都是3位数,以及3位数乘2位数为4位数
ans++; // 统计结果自增1(只有222*22满足此要求)
}
}
}
cout << ans << endl;
return 0;
}
【运行结果】
5
2 3 4 6 8
1