今天做了一下谷歌2013年校园招聘第二轮机试题,自己独立把程序写出来并且调试通过。
原题网址:https://code.google.com/codejam/contest/2929486/dashboard#s=p0
先说一下题目的大致意思:
1.输入一个整数N:3 ≤ N ≤ 6
2.输入一个N2xN2 阶矩阵
3.判断是否是数独:
数独必须同时满足以下三个条件:(1)每一行是从1到N2的互异整数
(2)每一列是从1到N2的互异整数
(3)把这个矩阵分为N2个不重叠的子矩阵,每个子矩阵包含1到N2的互异整数
例如:N = 3时,如图所示
是一个数独。
我的解题思路:
(1)先判断输入的数是否在1到N2范围内,如果不在,则说明不是数独。
(2)判断N2行和N2列是否是互异的元素:这里用到了标准库的容器set,把N2个数放入一个set中,然后调用set.size()函数,看其返回值是否等于N2,如果不等于N2,则不是数独。
(3)循环把N2个子矩阵的所有元素放入set中,然后调用set.size()函数,看其返回值是否等于N2,如果不等于N2,则不是数独。
下面直接上代码:
#include <iostream> #include <stdlib.h> #include <vector> #include <set> using namespace std; //判断一个n×n的矩阵的各行、各列元素是否互异 bool isSoduku(int *p,int n) { int i,j; bool b1 = false; bool b2 = false; for(i = 0;i < n;i++) { set<int> rs; for(j = 0;j < n;j++) { int temp = *(p + i*n + j); rs.insert(temp); } if(n == rs.size()) b1 = true; } for(j = 0;j < n;j++) { set<int> cs; for(i = 0;i < n;i++) { int t = *(p + i + j*n); cs.insert(t); } if(n == cs.size()) b2 = true; } return (b1 && b2); } int main() { int T; cin>>T; bool *re = new bool[T]; for(int l = 0;l < T;l++) re[l] = true; for(int i = 0;i < T;i++) { int n; cin>>n; int **a = new int *[n*n]; for(int r = 0;r < n*n;r++) a[r] = new int [n*n]; for(int j = 0;j < n*n;j++) { for(int k = 0;k < n*n;k++) { cin>>a[j][k]; if(a[j][k] < 1 || a[j][k] > n*n) re[i] = false; } } //如果输入的数不在1到N的平方的范围内,则继续测试下一个用例 if(!re[i]) continue; //如果矩阵各行、各列的数不互异,则继续测试下一个用例 if(!isSoduku((int*)a,n*n)) { re[i] = false; continue; } else { bool con = true; //循环测试N*N个子矩阵,看它们中的元素是否互异 for(int p = 0;p < n;p++) { if(!con) break; for(int q = 0;q < n;q++) { set<int> s; for(int x = 0;x < n;x++) { for(int y = 0;y < n;y++) s.insert(a[x + n*p][y + n*q]); } if(s.size() != n*n) { re[i] = false; con = false; break; } } } } for(int num = 0;num < n*n;num++) { delete[] a[num]; } delete a; } for(int i = 0;i < T;i++) { if(re[i]) cout<<"Case #"<<i+1<<":Yes"<<endl; else cout<<"Case #"<<i+1<<":No"<<endl; } delete re; return 0; }