华师一附中OI组
标题:
P1037 产生数
[打印本页]
作者:
倚窗倾听风吹雨
时间:
2018-10-3 18:47
标题:
P1037 产生数
https://www.luogu.org/problemnew/show/P1037
题目描述
给出一个整数n(n<300)和 k 个变换规则(k≤15)。
规则:
一位数可变换成另一个一位数:
规则的右部不能为零。
例如:n=234。有规则(k=2):
2->5
3->6
上面的整数234经过变换后可能产生出的整数为(包括原数):
234
534
264
564
共4 种不同的产生数
问题:
给出一个整数 n 和 k 个规则。
求出:
经过任意次的变换(0次或多次),能产生出多少个不同整数。
仅要求输出个数。
输入输出格式
输入格式:
键盘输入,格式为:
n k
x_1 y_1
x_2 y_2
... ...
x_n y_n
输出格式:
屏幕输出,格式为:
1个整数(满足条件的个数):
输入输出样例
输入样例#1:
234 2
2 5
3 6
输出样例#1:
4
作者:
倚窗倾听风吹雨
时间:
2018-10-3 19:03
#include<iostream>
#include<cstring>
#define FOR(i,a,b) for(register int i=a;i<=b;i++)
#define ROF(i,a,b) for(register int i=a;i>=b;i--)
using namespace std;
string n;
int len,k,m[11][3],c[200],ans[200];
bool num[11][11];
void add(int *a)
{
a[1]++;a[0]=1;
if(a[1]>=10){a[2]++;a[1]=0;a[0]=2;}
return;
}
void mul(int *a,int *b)
{
memset(c,0,sizeof(c));
int ex;
FOR(i,1,a[0])
{
ex=0;
FOR(j,1,b[0])
{
c[i+j-1]+=a[i]*b[j]+ex;
ex=c[i+j-1]/10;
c[i+j-1]%=10;
}
c[i+b[0]]+=ex;
}
c[0]=a[0]+b[0]+1;
while(c[0]>1 && !c[c[0]])c[0]--;
FOR(i,0,c[0])a[i]=c[i];
}
void print(int *a){ROF(i,a[0],1)cout<<a[i];cout<<endl;return;}
void Floyd()
{
FOR(k,0,9)FOR(i,0,9)FOR(j,0,9)if(num[i][k] && num[k][j])num[i][j]=1;
}
int main()
{
cin>>n>>k;FOR(i,0,9)num[i][i]=1;len=n.size();
FOR(i,1,k){int a,b;cin>>a>>b;num[a][b]=1;}
Floyd();///FOR(i,0,9){FOR(j,0,9)cout<<num[i][j]<<" ";cout<<endl;}
FOR(i,0,9)FOR(j,0,9)if(num[i][j])add(m[i]);//FOR(i,0,9)print(m[i]);
ans[0]=1;ans[1]=1;
FOR(i,0,len-1)mul(ans,m[n[i]-'0']);
print(ans);
return 0;
}
复制代码
欢迎光临 华师一附中OI组 (http://hsyit.cn/)
Powered by Discuz! X3.2