NO.1
题目:(来自ACdream)
C - 小晴天老师系列——竖式乘法
Time Limit: 4000/2000MS (Java/Others) Memory Limit: 128000/64000KB (Java/Others)
Problem Description
小晴天是ACdream团队中最牛的老师之一,他最擅长数学运算~这天他翻开一本《AC is not a dream》杂志,发现最后一页有一道很经典的思维题,题目很简单,每个框填写一个数字,构成一个竖式,每个数的最高位不能为0,但是有一些数字被隐藏掉了,然后让你根据没有隐藏的数字填出隐藏的数字。
如下图:
然后小晴天二话不说,三下五除二就写出了答案:
然后小晴天就觉得这样的题目太简单了,于是问你是否有办法来求出一道题目有多少种不同的答案呢?(只要有一个方框有不同的数字即为不同的答案)
Input
多组数据,首先是一个整数t(t<=20),表示数据组数。
对于每组数据,用5行表示一个竖式,每行均为一个字符串,仅含有星号(*)与数字('0'~'9')组成,其中星号表示空白
其中第一行为长度为3的字符串。
第二行为长度为2的字符串。
第三行为长度为4的字符串。
第四行为长度为3的字符串。
第五行为长度为5的字符串。
Output
对于每组数据,输出一个整数x,表示符合乘法竖式法则的填法的种类。
Sample Input
2
***
**
3384
846
*****
4**
**
3384
846
*****
Sample Output
2
1
Hint
样例1,除了题目中的那种情况,还有这种
而样例2,因为第一个数的百位被固定为4,故只有一种填法。
(-/--)具体思路:
首先开一个二维数组来存放输入,用两个for来遍历乘数,被乘数从100到999,乘数从10到99,将他们的各个位分开,对应二维数组的输入,如果二维数组中的该位不是*且不等于该数,说明这个数不满足条件,首先通过第一行和第二行的星号与否淘汰一部分数,再通过第三行和第四行淘汰一部分,如果剩下的还能通过最后一行的检测,计算器就++.
(-/--)AC代码:
#include<stdio.h>
int main()
{
int i,j,t,a,b,c,h1[1010],h2[110]; //h1和h2数组用来记录通过第一轮的数
int a1,a2,a3,a4,a5,co,h; //a1,a2等全部都是用来记录各个位的数字
char s[5][10]; //接收输入
while(scanf("%d",&t)!=EOF)
{
while(t--)
{
for(i=0;i<5;i++)
scanf("%s",s[i]);
//第一轮
for(i=100;i<1000;i++)
{
h1[i]=0;
a=i/100;
b=i%100/10;
c=i%10;
if(s[0][0]!='*'&&s[0][0]-'0'!=a) continue;
if(s[0][1]!='*'&&s[0][1]-'0'!=b) continue;
if(s[0][2]!='*'&&s[0][2]-'0'!=c) continue;
h1[i]=1; //满足条件
}
for(i=10;i<100;i++)
{
h2[i]=0;
a=i/10;
b=i%10;
if(s[1][0]!='*'&&s[1][0]-'0'!=a) continue;
if(s[1][1]!='*'&&s[1][1]-'0'!=b) continue;
h2[i]=1;
}
for(co=0,i=100;i<1000;i++) //co计数
{
if(h1[i]==1)
{
for(j=10;j<100;j++)
{
if(h2[j]==1)
{
a=j/10;
b=j%10;
if(i*b<1000) continue; //因为第三行有四位,所以相乘小于1000的淘汰
h=i*b;
a1=h/1000;
a2=h%1000/100;
a3=h%100/10;
a4=h%10;
if(s[2][0]!='*'&&s[2][0]-'0'!=a1) continue;
if(s[2][1]!='*'&&s[2][1]-'0'!=a2) continue;
if(s[2][2]!='*'&&s[2][2]-'0'!=a3) continue;
if(s[2][3]!='*'&&s[2][3]-'0'!=a4) continue;
if(i*a>999) continue; //同理
h=i*a;
a1=h/100;
a2=h%100/10;
a3=h%10;
if(s[3][0]!='*'&&s[3][0]-'0'!=a1) continue;
if(s[3][1]!='*'&&s[3][1]-'0'!=a2) continue;
if(s[3][2]!='*'&&s[3][2]-'0'!=a3) continue;
if(i*j<10000||i*j>99999) continue; //同理
h=i*j;
a1=h/10000;
a2=h%10000/1000;
a3=h%1000/100;
a4=h%100/10;
a5=h%10;
if(s[4][0]!='*'&&s[4][0]-'0'!=a1) continue;
if(s[4][1]!='*'&&s[4][1]-'0'!=a2) continue;
if(s[4][2]!='*'&&s[4][2]-'0'!=a3) continue;
if(s[4][3]!='*'&&s[4][3]-'0'!=a4) continue;
if(s[4][4]!='*'&&s[4][4]-'0'!=a5) continue;
co++;
}
}
}
}
printf("%d\n",co);
}
}
return 0;
}