hdu 3419 The Three Groups
#include<string.h> #include<stdio.h> #include <iostream> using namespace std; bool vis[15]; int a,b,c,s,res,e[15]; int data1,data2,data3; //求s个数的全排,并判断是否满足:data1*data2==data3 void perm(int k)//k从1开始 { int i; if(k==s+1)//s=a+b+c { data1=data2=data3=0; for(i=1; i<=a; i++) data1=10*data1+e[i]; for(; i<=a+b; i++) data2=10*data2+e[i]; for(; i<=s; i++) data3=10*data3+e[i]; if(data1*data2==data3) res++; } else //输出的所选数的排序 { for(i=k; i<=s; i++)//i从1到s { swap(e[k],e[i]); perm(k+1); swap(e[k],e[i]); //回溯 } } } //求组合1~9中选s(s=a+b+c)个数的组合 void dfs(int pos,int k)//pos(数字)从1开始,k~s(个数)从0开始 { if(k==s) perm(1); else { if(pos==10)//1~9的搜索 return; if(!vis[pos]) { vis[pos]=1; e[k+1]=pos; dfs(pos+1,k+1); vis[pos]=0; //回溯 } dfs(pos+1,k); } } int main() { while(cin>>a>>b>>c) { if(a==0&&b==0&&c==0) break; s=a+b+c; res=0; memset(vis,0,sizeof(vis)); if(a+b>=c && c>=(a>b?a:b)) dfs(1,0); cout<<res<<endl; } return 0; }
参考较优化代码:
#include"stdio.h" #include"string.h" int a,b,c; int ans; int hash[10]; int base[11],limit; int t_a; int t_b; void judge() { int i; int t; int temp[10]; t=t_a*t_b; if(limit<=t || t<base[c]) return ; memset(temp,0,sizeof(temp)); while(t) { if(hash[t%10]) return ; temp[t%10]=1; t/=10; } t=0; for(i=1;i<10;i++) if(temp[i]) t++; if(t!=c) return ; ans++; } void DFS2(int k) { int i; if(k>=base[b+1]) return ; if(base[b]<=k) {t_b=k;judge();return ;} for(i=1;i<10;i++) { if(hash[i]==0) { hash[i]=1; DFS2(k*10+i); hash[i]=0; } } } void DFS(int k) { int i; if(k>=base[a+1]) return; if(base[a]<=k) { t_a=k; DFS2(0); return ; } for(i=1;i<10;i++) { if(hash[i]==0) { hash[i]=1; DFS(k*10+i); hash[i]=0; } } } int main() { int i; while(scanf("%d%d%d",&a,&b,&c),a||b||c) { if(a==0 || b==0 || c==0) {printf("0\n");continue;} if(a+b-2>c) {printf("0\n");continue;} base[1]=1; for(i=2;i<=10;i++) base[i]=base[i-1]*10; limit=base[c+1]; ans=0; memset(hash,0,sizeof(hash)); DFS(0); printf("%d\n",ans); } return 0; }