UESTC Training for Data Structures——C
2012-05-02 21:19
267 查看
Problem C
In the game, God Wu will give you a rectangular grid of letters, in which several words are hidden. Each word may begin anywhere in the puzzle, and may be oriented in any straight line horizontally, vertically, or diagonally. However, the words must all go
down, right, or down-right. A dictionary is also given to you, indicating the words to be found in the grid.
You task is to find the locations of each word within the grid.If you cannot do it,God Wu will give you some color to see see!
For each of the test cases:
The first line is three integers R C and M separated by whitespaces. R (20 ≤ R ≤ 500) is the number of rows of the grid. C (20 ≤ C ≤ 500) is the number of columns of the grid.M(M<=10000) is the number of words to be found.
The following R lines, each line will contains exactly C characters without anything else. Each character is in the range 'A' - 'Z'.
The following M lines, each line contains a unique word in the dictionary. Each word will contain between 1 and 20 characters ( also in the range 'A' - 'Z').
be found more than once, the location in the lowest-indexed row should be returned. If there is still a tie, return the location with the lowest-indexed column. If a word cannot be found in the grid, return "-1 -1" for the word.
Problem Description
Recently,our God Wu invented a little game named "God Wu's Puzzle" . If you dont know it, what a pity !In the game, God Wu will give you a rectangular grid of letters, in which several words are hidden. Each word may begin anywhere in the puzzle, and may be oriented in any straight line horizontally, vertically, or diagonally. However, the words must all go
down, right, or down-right. A dictionary is also given to you, indicating the words to be found in the grid.
You task is to find the locations of each word within the grid.If you cannot do it,God Wu will give you some color to see see!
Input
The first line is a single integer T,the number of test cases.(T<=25)For each of the test cases:
The first line is three integers R C and M separated by whitespaces. R (20 ≤ R ≤ 500) is the number of rows of the grid. C (20 ≤ C ≤ 500) is the number of columns of the grid.M(M<=10000) is the number of words to be found.
The following R lines, each line will contains exactly C characters without anything else. Each character is in the range 'A' - 'Z'.
The following M lines, each line contains a unique word in the dictionary. Each word will contain between 1 and 20 characters ( also in the range 'A' - 'Z').
Output
For each word, output the "ROW COL"(quotes for clarity) pair, where ROW is the 0-based row in which the first letter of the word is found, and COL is the 0-based column in which the first letter of the word is found. If the same word canbe found more than once, the location in the lowest-indexed row should be returned. If there is still a tie, return the location with the lowest-indexed column. If a word cannot be found in the grid, return "-1 -1" for the word.
Sample Input
1 3 5 4 HENRY GAVIN MAGIC HENRY HGM HAG MAVIN
Sample Output
0 0 0 0 0 0 -1 -1
/*根据给的查询来建立字典树,然后在矩阵中看是否存在这个字符串*/ #include<iostream> #include<cstdio> #include<cstring> #include<cmath> #include<cstdlib> using namespace std; struct data { bool fg; int num; data *next[26]; } a[400000]; //由于多组case,每次动态分配内存后要释放内存很麻烦,我就用的数组的地址来分配给字典树的节点 data *root=&a[0]; int tot; struct dat { int x,y; }; const int zl[3][2]={0,1,1,1,1,0}; //方向增量,枚举三个方向 data *creat() //从数组中分配一个新的节点的地址,返回指针 { data *p=&a[++tot]; p->fg=false; for(int i=0;i<26;i++) p->next[i]=NULL; p->num=0; return p; } void insert(char *s,int k) //将序号为 k 的 s[] 这个单词插入字典树中 { int len=strlen(s); data *now=root; for(int i=0;i<len;i++) { int p=s[i]-'A'; if(now->next[p]==NULL) now->next[p]=creat(); now=now->next[p]; } now->fg=true; now->num=k; } int main() { int t,n,m,q; scanf("%d",&t); while(t--) { tot=0; dat ans[10005]; memset(ans,-1,sizeof(ans)); //先假设都找不到 for(int i=0;i<26;i++) root->next[i]=NULL; //赋初值 root->fg=false; root->num=0; char s[601][601]; scanf("%d%d%d",&n,&m,&q); getchar(); //n行 m 列 q 个询问 for(int i=0;i<n;i++) gets(s[i]); for(int i=1;i<=q;i++) { gets(s[600]); insert(s[600],i); } for(int i=0;i<n;i++) //行 for(int j=0;j<m;j++) //列 for(int k=0;k<3;k++) //枚举三个方向 { data *now=root; int x=i,y=j; while(x<n && y<m) { int p=s[x][y]-'A'; if(now->next[p]==NULL) break; now=now->next[p]; if(now->fg && ans[now->num].x==-1) //如果以前没有找到,当前的解就是最小的解 { ans[now->num].x=i; ans[now->num].y=j; } x+=zl[k][0]; y+=zl[k][1]; } } for(int i=1;i<=q;i++) //输出结果 printf("%d %d\n",ans[i].x,ans[i].y); } return 0; }
相关文章推荐
- 2014 UESTC Training for Data Structures—— E - 休生伤杜景死惊开
- UESTC Training for Data Structures——M
- 2016 UESTC Training for Data Structures N - 秋实大哥搞算数 用栈处理表达式
- 2016 UESTC Training for Data Structures B - 卿学姐与基本法 CDOJ 1325 线段树+离散化
- 2016 UESTC Training for Data Structures R - Japan CDOJ 383 树状数组 逆序对
- UESTC_秋实大哥与战争 2015 UESTC Training for Data Structures<Problem D>
- 2016 UESTC Training for Data Structures O - 卿学姐种美丽的花 树状数组+等差数列
- 2016 UESTC Training for Data Structures C - 卿学姐与诡异村庄 CDOJ 1328 并查集
- UESTC_秋实大哥与家 2015 UESTC Training for Data Structures<Problem E>
- 2016 UESTC Training for Data Structures Q - 昊昊爱运动 II 线段树+延迟操作+bitset
- 2016 UESTC Training for Data Structures D - 卿学姐与魔法 CDOJ 1329 堆
- UESTC_秋实大哥与妹纸 2015 UESTC Training for Data Structures<Problem F>
- qscoj 66 ||2017 UESTC Training for Data Structures D(离线+树状数组)
- 2016 UESTC Training for Data Structures (1)
- UESTC Training for Data Structures(总结)
- 2016 UESTC Training for Data Structures C -> 卿学姐与诡异村庄 CDOJ 1328 并查集
- 2016 UESTC Training for Data Structures R - Japan 树状数组求逆序数
- 2016 UESTC Training for Data Structures E - 卿学姐与城堡的墙 CDOJ 1341 树状数组 逆序对 离散化
- UESTC_秋实大哥去打工 2015 UESTC Training for Data Structures<Problem G>
- 2015 UESTC Training for Data Structures 秋实大哥下棋