您的位置:首页 > 其它

hdoj 5612 Baby Ming and Matrix games 【DFS 暴力】

2016-01-23 22:19 281 查看


Baby Ming and Matrix games

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)

Total Submission(s): 83    Accepted Submission(s): 26

Problem Description

These few days, Baby Ming is addicted to playing a matrix game.

Given a n∗m matrix,
the character in the matrix(i∗2,j∗2) (i,j=0,1,2...) are
the numbers between 0−9.
There are an arithmetic sign (‘+’, ‘-‘, ‘∗’,
‘/’) between every two adjacent numbers, other places in the matrix fill with ‘#’.

The question is whether you can find an expressions from the matrix, in order to make the result of the expressions equal to the given integer sum.
(Expressions are calculated according to the order from left to right)

Get expressions by the following way: select a number as a starting point, and then selecting an adjacent digital X to make the expressions, and then, selecting the location of X for the next starting point. (The number in same place can’t be used twice.)

 

Input

In the first line contains a single positive integer T,
indicating number of test case.

In the second line there are two odd numbers n,m,
and an integer sum(−1018<sum<1018,
divisor 0 is not legitimate, division rules see example)

In the next n lines,
each line input m characters,
indicating the matrix. (The number of numbers in the matrix is less than 15)

1≤T≤1000

 

Output

Print Possible if it is possible to find such an expressions.

Print Impossible if it is impossible to find such an expressions.

 

Sample Input

3
3 3 24
1*1
+#*
2*8
1 1 1
1
3 3 3
1*0
/#*
2*6

 

Sample Output

Possible
Possible
Possible

Hint
The first sample:1+2*8=24
The third sample:1/2*6=3

 

题意:

铭宝宝喜欢玩游戏,这两天他喜欢玩下面这个游戏了。
给出一个n*mn∗m的矩阵,矩阵的(i*2,j*2)(i∗2,j∗2) (其中i, j = 0, 1, 2...i,j=0,1,2...) 位置上为0~9的数字,矩阵中每两个数字中间有一个算术符号(+、-、*、/),其他位置用#填充。
问题是:是否能在上述矩阵中,找到一个表达式,使得表达式的计算结果为给出的sum(表达式从左到右计算)
表达式按照如下方式获取:选择一个数字作为起点,每次选择相邻的数字XX进行一次计算,把得到的结果保存在数字XX上,并选择该位置为下一个起点(同一个位置的数字不能使用22次)。


输入描述
输入T(T \leq 1,000)T(T≤1,000)表示测试组数
输入33个数,奇数n,mn,m以及整数sumsum(除0的式子是不合法的,除法规则见样例,-10^{18} < sum < 10^{18}−10​18​​<sum<10​18​​)
接下来输入nn行,每行mm个字符,表示给出的矩阵(矩阵内的数字个数\leq 15≤15)


输出描述
输出Possible,表示能够找到这样的表达式
输出Impossible,表示不能够找到这样的表达式


输入样例
3
3 3 24
1*1
+#*
2*8
1 1 1
1
3 3 3
1*0
/#*
2*6


输出样例
Possible
Possible
Possible


直接暴力DFS就OK了。 分子分母过大的话可以去掉GCD,不过不去好像也能过。

AC代码:

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <vector>
#include <string>
#define INF 0x3f3f3f3f
#define eps 1e-8
#define MAXN (1000+10)
#define MAXM (200000+10)
#define Ri(a) scanf("%d", &a)
#define Rl(a) scanf("%lld", &a)
#define Rf(a) scanf("%lf", &a)
#define Rs(a) scanf("%s", a)
#define Pi(a) printf("%d\n", (a))
#define Pf(a) printf("%.2lf\n", (a))
#define Pl(a) printf("%lld\n", (a))
#define Ps(a) printf("%s\n", (a))
#define W(a) while((a)--)
#define CLR(a, b) memset(a, (b), sizeof(a))
#define MOD 1000000007
#define LL long long
#define lson o<<1, l, mid
#define rson o<<1|1, mid+1, r
#define ll o<<1
#define rr o<<1|1
#define PI acos(-1.0)
using namespace std;
char str[50][50];
bool vis[50][50];
int Move[4][2] = {0,2, 0,-2, 2,0, -2,0};
__int64 sum;
__int64 gcd(__int64 a, __int64 b){
return b == 0 ? a : gcd(b, a%b);
}
bool flag;
int n, m;
bool judge(int x, int y){
return x >= 0 && x < n && y >= 0 && y < m;
}
void DFS(int x, int y, __int64 a, __int64 b)
{
if(flag) return ;
if(a == b * sum)
{
flag = true;
return ;
}
for(int k = 0; k < 4; k++)
{
int xx = x + Move[k][0];
int yy = y + Move[k][1];
if(!judge(xx, yy) || vis[xx][yy] || str[xx][yy] < '0' || str[xx][yy] > '9' || str[xx][yy] == '#') continue;
int mx = (xx + x) >> 1;
int my = (yy + y) >> 1;
__int64 v = str[xx][yy] - '0';
__int64 aa = a, bb = b;
if(str[mx][my] == '/' && v == 0) continue;
vis[xx][yy] = true;
if(str[mx][my] == '*') {aa *= v;}
else if(str[mx][my] == '/') {bb *= v;}
else if(str[mx][my] == '+') {aa += bb * v;}
else {aa -= bb * v;}
__int64 c = gcd(aa, bb); aa /= c, bb /= c;
DFS(xx, yy, aa, bb);
vis[xx][yy] = false;
}
}
int main()
{
int t; Ri(t);
W(t)
{
Ri(n); Ri(m);
scanf("%I64d", &sum);
for(int i = 0; i < n; i++)
Rs(str[i]);
flag = false;
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m; j++)
{
if(str[i][j] >= '0' && str[i][j] <= '9')
{
__int64 val = str[i][j] - '0';
CLR(vis, false); vis[i][j] = true;
DFS(i, j, val, 1);
if(flag)
break;
}
}
if(flag) break;
}
printf(flag ? "Possible\n" : "Impossible\n");
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: