题目描述 Description

所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母。来看一个简单的例子:

43#9865#045
    +    8468#6633
       44445506978

其中#号代表被虫子啃掉的数字。根据算式,我们很容易判断:第一行的两个数字分别是5和3,第二行的数字是5。

现在,我们对问题做两个限制:

首先,我们只考虑加法的虫食算。这里的加法是N进制加法,算式中三个数都有N位,允许有前导的0。


次,虫子把所有的数都啃光了,我们只知道哪些数字是相同的,我们将相同的数字用相同的字母表示,不同的数字用不同的字母表示。如果这个算式是N进制的,我
们就取英文字母表午的前N个大写字母来表示这个算式中的0到N-1这N个不同的数字:但是这N个字母并不一定顺序地代表0到N-1)。输入数据保证N个字
母分别至少出现一次。

BADC
      +    CBDA
            DCCC

上面的算式是一个4进制的算式。很显然,我们只要让ABCD分别代表0123,便可以让这个式子成立了。你的任务是,对于给定的N进制加法算式,求出N个不同的字母分别代表的数字,使得该加法算式成立。输入数据保证有且仅有一组解,

输入描述
Input Description

输入包含4行。第一行有一个正整数N(N<=26),后面的3行每行有一个由大写字母组成的字符串,分别代表两个加数以及和。这3个字符串左右两端都没有空格,从高位到低位,并且恰好有N位。

输出描述
Output Description

输出包含一行。在这一行中,应当包含唯一的那组解。解是这样表示的:输出N个数字,分别表示A,B,C……所代表的数字,相邻的两个数字用一个空格隔开,不能有多余的空格。

样例输入
Sample Input

5
ABCED
BDACE
EBBAA

样例输出
Sample Output

1 0 3 4 2

数据范围及提示
Data Size & Hint

对于30%的数据,保证有N<=10;
对于50%的数据,保证有N<=15;
对于全部的数据,保证有N<=26。

 
 
正解:搜索解题报告:
  今天考搜索专题的时候考了这道题,结果只有80分,一个T一个WA。

  仔细查了一下错,发现又犯低级错误了。首先我的下标从0开始那么我的搜索边界应该是-1,然而我只到了0,导致有个解没搜到。然后我打的只是裸搜索,没有一个很优秀的剪枝,就是每一步都check一下,还没搜到的等式是不是已经三个都出来了,如果已经都确定了,但是不管进不进位都无法做到的话,那就说明不合法,可以直接return。这样剪枝的话就跑得很快了,基本0.008s就可以过了。

  其余的就是裸搜索啦:

 
 //It is made by jump~
#include <iostream>
#include <cstdlib>
#include <cstring>
#include <cstdio>
#include <cmath>
#include <algorithm>
#include <ctime>
#include <vector>
#include <queue>
#include <map>
#include <set>
using namespace std;
typedef long long LL;
#define RG register
const int MAXN = ;
int n,ce,a[MAXN],b[MAXN],c[MAXN];
int match[MAXN],ans[MAXN];
char ch[MAXN];
bool ok,vis[MAXN]; inline int getint()
{
RG int w=,q=; RG char c=getchar();
while((c<'' || c>'') && c!='-') c=getchar(); if(c=='-') q=,c=getchar();
while (c>='' && c<='') w=w*+c-'', c=getchar(); return q ? -w : w;
} inline void dfs(RG int x,RG int type,RG int remain){
if(ok) return ; RG int ans1,ans2,ans3;
for(int i=;i<x;i++) {//进位最多是ce,如果某一位已经确定,但是进位不够则不合法
ans1=match[a[i]],ans2=match[b[i]],ans3=match[c[i]];
if(ans1==-||ans2==-||ans3==-) continue;
if( ((ans3-ans2-ans1)%n+n)%n >ce) return ;
} if(x==-) {//!!!!!!!
for(RG int i=;i<n;i++) { ans[i]=match[i]; if(match[i]==-) return ; }
ok=true; return ;
}
if(type==) {//搜第一个
if(match[a[x]]!=-) dfs(x,type+,remain);
else{
for(RG int i=n-;i>=;i--) {
if(vis[i]) continue;
vis[i]=; match[a[x]]=i; dfs(x,type+,remain);
vis[i]=; match[a[x]]=-;
}
}
}
else{//搜第二个加数的这一位
ans1=match[a[x]],ans2=match[b[x]],ans3=match[c[x]];
if(ans2!=-) {
RG int sheng=ans1+ans2+remain;
if(sheng%n==ans3) dfs(x-,,sheng/n);
else if(ans3==-) {
vis[sheng%n]=; match[c[x]]=sheng%n; dfs(x-,,sheng/n);
vis[sheng%n]=; match[c[x]]=-;
}
}
else{
RG int cc,ss;
for(RG int i=n-;i>=;i--) {
if(vis[i]) continue;
ss=ans1+i+remain; cc=ss%n;
if(cc!=ans3 && ans3!=-) continue;
if(ans3==-) {
if(vis[cc]) continue;
vis[cc]=; match[c[x]]=cc;
}
vis[i]=; match[b[x]]=i;
dfs(x-,,ss/n);
vis[i]=; match[b[x]]=-;
if(ans3==-) {
vis[cc]=; match[c[x]]=-;
}
}
}
}
} inline void work(){
n=getint(); for(RG int i=;i<=n;i++) match[i]=-; ce=*n-; ce/=n;
scanf("%s",ch); for(RG int i=;i<n;i++) a[i]=ch[i]-'A';
scanf("%s",ch); for(RG int i=;i<n;i++) b[i]=ch[i]-'A';
scanf("%s",ch); for(RG int i=;i<n;i++) c[i]=ch[i]-'A';
ok=false; dfs(n-,,);
printf("%d",ans[]); for(RG int i=;i<n;i++) printf(" %d",ans[i]);
} int main()
{
work();
return ;
}

codevs1064 虫食算的更多相关文章

  1. 洛谷 P1092 虫食算 Label:dfs

    题目描述 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子: 43#9865#045 +8468#6633 44445509678 其中# ...

  2. 深度优先搜索 codevs 1064 虫食算

    codevs 1064 虫食算 2004年NOIP全国联赛提高组  时间限制: 2 s  空间限制: 128000 KB  题目等级 : 钻石 Diamond   题目描述 Description 所 ...

  3. NOIP2004 虫食算

    描述 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子:43#9865#045+ 8468#6633= 44445506678其中#号代表 ...

  4. Codevs 1064 虫食算 2004年NOIP全国联赛提高组

    1064 虫食算 2004年NOIP全国联赛提高组 时间限制: 2 s 空间限制: 128000 KB 题目等级 : 钻石 Diamond 题目描述 Description 所谓虫食算,就是原先的算式 ...

  5. Luogu P1092 虫食算

    题目描述 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子: 43#9865#045 +8468#6633 44445509678 其中# ...

  6. 【NOIP2004】【CJOJ1703】【洛谷1092】虫食算

    题面 题目描述 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子: 43#9865#045 +8468#6633 44445509678 ...

  7. 【NOIP2004】虫食算

    Description 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子: 43#9865#045 +. 8468#6633 444455 ...

  8. 洛谷P1092 虫食算

    P1092 虫食算 题目描述 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子: http://paste.ubuntu.com/2544 ...

  9. 【题解】 P1092虫食算

    [题解]P1092 虫食算 老题了,很经典. 用到了一些搜索套路. 可行性剪枝,劣者靠后,随机化,\(etc......\) 搜索设参也很有技巧,设一个\(adjustment\)参数可以很方便地在两 ...

随机推荐

  1. WPF标注装饰器

    标注 在许多地方我们都会用到标注,比如在画图中: 在Office中: 在Foxit Reader中: 在Blend中: 等等. 简介 以前,因项目上需要做标注,简单找了一下,没发现适合要求的控件(包括 ...

  2. 观察器observes与对象初始化

    Demo.Person2 = Ember.Object.extend({ init: function() { alert('lljsd'); this.set('salutation', " ...

  3. ST3插件——PlainTasks的使用

    今天看到一个有意思的ST3插件,可以进行简单的任务管理. 安装很简单:ctrl + shift + p,输入install回车,再输入plaintasks回车即可. 以下是一些支持的操作,更多的操作请 ...

  4. 一道看似简单的sql需求却难倒各路高手 - 你也来挑战下吗?

    转自:http://www.cnblogs.com/keguangqiang/p/4535046.html 听说这题难住大批高手,你也来试下吧.ps:博问里的博友提出的. 原始数据 select *  ...

  5. CLR Profiler

    检查c#代码内存泄露工具-CLR Profiler 大家都知道.net有一套自己的内存(垃圾)回收机制,除非有一些数据(方法)长期占有内存不随着垃圾回收功能而释放内存,这样就造成了我们经常说的内存泄露 ...

  6. 发发关于JavaScript的感慨,随手记几个js知识碎片

    最近一段时间写了很多JavaScript和jquery代码,越来越感觉js基础不牢固,写一句查半天,有时间肯定要系统的学一下. 不说了,先记一下最近学到的点东西,省的以后没时间系统学js还要再来查. ...

  7. php基础06:运算符

    <?php //1.PHP 字符串运算符: 串接 $str1 = "gao"; $str1 = $str1."xiong"; echo $str1; ec ...

  8. php基础04:字符串函数

    <?php //1.strlen(),strlen() 函数返回字符串的长度,以字符计. echo strlen("hello world"); echo "< ...

  9. Asp.net与Dojo交互:仪器仪表实现

    项目中需要用到仪器仪表的界面来显示实时的采集信息值,于是便遍地寻找,参考了fusionchart和anychart之后,发现都是收费的,破解的又没有这些功能,只好作罢.之后又找遍了JQuery的插件, ...

  10. 获取元素的xpath, 转换xpath为csspath进行jQuery元素获取

    获取元素的xpath, 转换xpath为csspath进行jQuery元素获取 博客分类: 编程心得 jQueryCSSHTML  var $shadow = new Object(); /** 获取 ...