判斷一個點陣中含有幾個正方形(數正方形)
如圖例中:有2個邊長爲1的正方形,1個邊長爲2的正方形
4 表示每行每列各有4個頂點 16 表示整個點陣中共有16條邊 H 1 1 H表示水平邊 從(1,1)->(1,2)之間有一條邊 注意:1 1 表示水平第一行第一個頂點 H 1 3 H 2 1 H 2 2 H 2 3 H 3 2 H 4 2 H 4 3 V 1 1 V表示垂直邊 從(1,1)->(2,1)之間有一條邊 注意:1 1 表示垂直看第一列第一個頂點 V 2 1 V 2 2 V 2 3 V 3 2 V 4 1 V 4 2 V 4 3
2 3 H 1 1 H 2 1 V 2 1
#define _CRT_SECURE_NO_WARNINGS #include <stdio.h> #include <stdlib.h> #include <string.h> #define N 9 int n,m; int edge[N*N][3]; //邊信息 int square[N+1][N+1]; //正方形頂點信息,從(1,1)開始
void getInfo() { //獲取頂點、邊數 scanf("%d", &n); scanf("%d", &m); //將邊信息轉換爲正方形信息 memset(square, sizeof(square), 0); //獲取邊信息 for (int i = 0; i < m; i++) { getchar(); scanf("%c %d %d", (char*)&edge[i][0], &edge[i][1], &edge[i][2]); //注意1表示水平有邊,2表示垂直有邊,既有水平,又有垂直爲3 //注意V的時候 V 2 1 是表明第二列第一個 edge[i][0] == 'H' ? square[edge[i][1]][edge[i][2]] += 1 : square[edge[i][2]][edge[i][1]] += 2; } }
int getNumForSq(int ec) { //從正方形左上角開始從上到下,從左到右 int num = 0,x,y; for (int i = 1; i <= n - ec;i++) //列 { for (int j = 1; j <= n - ec;j++) //行 { if (square[j][i]!=0) //此處有頂點 { //開始判斷是否有指定大小正方形 x = j, y = i; //判斷上橫邊 for (y = i; y <= i + ec-1; y++) if (!(square[x][y] == 1 || square[x][y] == 3)) goto Next; //判斷下橫邊 x = j + ec, y = i; for (y = i; y <= i + ec-1; y++) if (!(square[x][y] == 1 || square[x][y] == 3)) goto Next; //判斷左邊 x = j, y = i; for (x = j; x <= j + ec-1;x++) if (!(square[x][y] == 2 || square[x][y] == 3)) goto Next; //判斷右邊 x = j, y = i + ec; for (x = j; x <= j + ec-1; x++) if (!(square[x][y] == 2 || square[x][y] == 3)) goto Next; //構成正方形 num++; } Next:; } } return num; }
int main() { FILE* fp=freopen("data2.in", "r", stdin); freopen("data2.out", "w", stdout); int i = 1, j,num,flag; while (!feof(fp)) { //獲取一組信息 flag = 0; getInfo(); printf("Problem #%d\n\n", i++); //開始進行計算正方形大小 從1->n-1 for (j = 1; j < n;j++) { num = getNumForSq(j); if (num) { printf("%d square(s) of size %d\n", num, j); flag = 1; } } flag ? printf("\n**************************\n\n") : printf("No completed squares can be found.\n"); } freopen("CON", "r", stdin); freopen("CON", "w", stdout); return 0; }