题意:给出一个数字谜,要求修改尽量少的数,使修改后的数字谜只有唯一解。空格和数字可以随意替换,但不能增删,数字谜中所有涉及的数必须是没有前导零的正数。输入数字谜一定形如a*b=c,其中a、b、c分别最多有2、2、4位。
分析:

1、因为输出字典序最小,所以每一位数按“*0123456789”顺序枚举。

2、如果当前要修改的数与即将被修改的数相同,则cnt不加1。

3、检查积的时候,为防超时,只枚举两个乘数,通过检查积的位数和积的已确定数字来验证。

4、遇到空格要跳过并检查返回结果。

#pragma comment(linker, "/STACK:102400000, 102400000")
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cctype>
#include<cmath>
#include<iostream>
#include<sstream>
#include<iterator>
#include<algorithm>
#include<string>
#include<vector>
#include<set>
#include<map>
#include<stack>
#include<deque>
#include<queue>
#include<list>
#define Min(a, b) ((a < b) ? a : b)
#define Max(a, b) ((a < b) ? b : a)
typedef long long ll;
typedef unsigned long long llu;
const int INT_INF = 0x3f3f3f3f;
const int INT_M_INF = 0x7f7f7f7f;
const ll LL_INF = 0x3f3f3f3f3f3f3f3f;
const ll LL_M_INF = 0x7f7f7f7f7f7f7f7f;
const int dr[] = {, -, , , -, -, , };
const int dc[] = {-, , , , -, , -, };
const int MOD = 1e9 + ;
const double pi = acos(-1.0);
const double eps = 1e-;
const int MAXN = + ;
const int MAXT = + ;
using namespace std;
string s;
map<int, pair<int, int> > mp;//3个字符串的起始终止下标
const string ss = "*0123456789";
int maxn;
int len;
int num;
int changetodigit(string t){
int l = t.size();
int ans = ;
for(int i = ; i < l; ++i){
ans = ans * + t[i] - '';
}
return ans;
}
bool check(){//检查积是否合法
int x = changetodigit(s.substr(mp[].first, mp[].second - mp[].first + ));
int y = changetodigit(s.substr(mp[].first, mp[].second - mp[].first + ));
char str[];
sprintf(str, "%d", x * y);
int l = strlen(str);
if(mp[].second - mp[].first + != l) return false;//位数不相同
for(int i = mp[].first; i <= mp[].second; ++i){
if(s[i] == '*') continue;
if(s[i] != str[i - mp[].first]) return false;
}
return true;
}
bool leadingzero(int cur){//判断当前下标是否为数字的第一位
for(int i = ; i < ; ++i){
if(mp[i].first == cur) return true;
}
return false;
}
void judge(int cur){
if(num > ) return;
if(cur == mp[].second + ){
if(check()) ++num;
return;
}
if(s[cur] != '*') judge(cur + );
else{
for(int i = ; i < ; ++i){
if(i == && leadingzero(cur)) continue;
s[cur] = ss[i];
judge(cur + );
s[cur] = '*';
}
}
}
bool dfs(int cnt, int cur){
if(cnt >= maxn){
string tmp = s;
num = ;
judge();
s = tmp;
if(num == ){
return true;
}
return false;
}
if(cur == len) return false;
if(s[cur] == ' '){
if(dfs(cnt, cur + )) return true;
return false;
}
else{
char c = s[cur];
for(int i = ; i < ; ++i){
if(i == && leadingzero(cur)) continue;
if(c == ss[i]){//如果当前要修改的数与即将被修改的数相同
if(dfs(cnt, cur + )) return true;
}
else{
s[cur] = ss[i];
if(dfs(cnt + , cur + )) return true;
s[cur] = c;
}
}
return false;
}
}
int main(){
int kase = ;
while(getline(cin, s)){
if(s[] == '') return ;
len = s.size();
int cnt = ;
int st = ;
for(int i = ; i < len; ++i){
if(s[i] == ' '){
mp[cnt++] = pair<int, int>(st, i - );
st = i + ;
}
}
mp[cnt++] = pair<int, int>(st, len - );
printf("Case %d: ", ++kase);
for(maxn = ; ; ++maxn){
if(dfs(, )){
printf("%s\n", s.c_str());
break;
}
}
}
return ;
}

UVA - 12107 Digit Puzzle(数字谜)(IDA*)的更多相关文章

  1. UVA_Digit Puzzle UVA 12107

    If you hide some digits in an integer equation, you create a digit puzzle. The figure below shows tw ...

  2. UVa 1225 Digit Counting --- 水题

    UVa 1225 题目大意:把前n(n<=10000)个整数顺次写在一起,12345678910111213...,数一数0-9各出现多少字 解题思路:用一个cnt数组记录0-9这10个数字出现 ...

  3. UVa 1583 Digit Generator --- 水题+打表

    UVa 1583 题目大意:如果x加上x的各个数字之和得到y,那么称x是y的生成元. 给定数字n,求它的最小生成元 解题思路:可以利用打表的方法,提前计算出以i为生成元的数,设为d,并保存在a[d]中 ...

  4. 紫书 习题7-8 UVa 12107 (IDA*)

    参考了这哥们的博客 https://blog.csdn.net/hyqsblog/article/details/46980287  (1)atoi可以char数组转int, 头文件 cstdlib ...

  5. UVA - 1343 The Rotation Game (BFS/IDA*)

    题目链接 紫书例题. 首先附上我第一次bfs+剪枝TLE的版本: #include<bits/stdc++.h> using namespace std; typedef long lon ...

  6. UVa 1583 Digit Generator(数学)

     题意 假设a加上a全部数位上的数等于b时 a称为b的generator  求给定数的最小generator 给的数n是小于100,000的  考虑到全部数位和最大的数99,999的数位和也才45 ...

  7. UVa 10533 - Digit Primes

    题目:输出给定区间中,本身是素数,而且这个数的各位之和也是素数的数(称为位素数)的个数. 分析:数论.首先利用筛法,求出1000000内的全部的素数:然后在利用生成的素数表, 推断每一个数是不是各位之 ...

  8. UVa 1343 旋转游戏(dfs+IDA*)

    https://vjudge.net/problem/UVA-1343 题意:如图所示,一共有8个1,8个2和8个3,如何以最少的移动来使得中间8个格子都为同一个数. 思路:状态空间搜索问题. 用ID ...

  9. UVa 11212 编辑书稿(dfs+IDA*)

    https://vjudge.net/problem/UVA-11212 题意:给出n个自然段组成的文章,将他们排列成1,2...,n.每次只能剪切一段连续的自然段,粘贴时按照顺序粘贴. 思路:状态空 ...

随机推荐

  1. GIMP

    1. 认识GIMP 2. GIMP与Photoshop的对比 3. GIMP官方手册教程 4. 2本GIMP的外文书下载 5. 2个外部入门教程 6. 其他相关软件 1. 认识GIMP GIMP是可用 ...

  2. Day3-B-Round Marriage CodeForces-981F

    It's marriage season in Ringland! Ringland has a form of a circle's boundary of length LL. There are ...

  3. 嵊州普及Day4T1

    题意:从n个数中选出k个数,使他们任意两数之差都等于m. 思路:任意差值都等于m,不就等价于k个数模m余数相同吗? 然后桶排储蓄一下各数余数即可. 见代码: #include<iostream& ...

  4. java实现在线预览 - -之poi实现word、excel、ppt转html

    简介 java实现在线预览功能是一个大家在工作中也许会遇到的需求,如果公司有钱,直接使用付费的第三方软件或者云在线预览服务就可以了,例如永中office.office web 365(http://w ...

  5. Golang编程的工程管理

    Golang编程的工程管理 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任.

  6. KAZE特征和各向异性扩散滤波

    kaze feature: http://www.doc88.com/p-6911376909693.html 各向异性扩散滤波  Scale-space and edge detection usi ...

  7. Day8 - E - The very same Munchhausen CodeForces - 1120E

    A positive integer aa is given. Baron Munchausen claims that he knows such a positive integer nn tha ...

  8. 关于无法下载sklearn中的MNIST original数据集的问题

    在使用Sklearn进行加载自带的数据集MNIST时,总是报错,代码及相应的错误显示如下: from sklearn.datasets import fetch_mldata mnist = fetc ...

  9. redis.conf文件配置

    最重要三个配置 1. bind 127.0.0.1 需要注释掉这一行,使别的主机可以访问 2. daemonize no 需要改为yes,使其后台运行 3. requirepass foobared ...

  10. P1052 卖个萌

    P1052 卖个萌 转跳点: