2016-02-17 25 views
-6

我已經用C編寫了一個程序來查找在另一個模式內是否存在模式。這兩種模式都是二維字符數組。 爲了進一步解釋,請考慮下面的情況。當在C中提供一個巨大的輸入時,在Linux中取消調用錯誤

假設圖案A是

1234567890 
0987654321 
1111111111 
1111111111 
2222222222 

和圖案B是

876543 
111111 
111111 

在這種情況下,模式B存在內部圖案A.從第二行和第三列開始。

以下是我的代碼。

#include <stdio.h> 
#include <stdlib.h> 

int main() 
{ 
    int t, T, R, C, r, c; 
    char** arr; 
    char ** pat; 
    int i, j, x, y, m = 0, n = 0, count = 0, brk_flag = 0, brk_flag2 = 0, found = 0; 

    freopen("C:\\test.txt", "r", stdin); 

    scanf("%d", &T); 
    for (t = 0; t<T; t++) { 

     scanf("%d%d", &R, &C); 
     arr = (char**)malloc(R * sizeof(char*)); 
     if (arr == NULL) { 
      printf("Unable to allocate memory."); 
      exit(1); 
     } 


     for (i = 0; i < R; i++) { 

      arr[i] = (char*)malloc(C * sizeof(char)); 
      scanf("%s", arr[i]); 

     } 

     scanf("%d%d", &r, &c); 
     pat = (char**)malloc(r * sizeof(char*)); 
     if (pat == NULL) { 
      printf("Unable to allocate memory."); 
      exit(1); 
     } 

     for (i = 0; i < r; i++) { 

      pat[i] = (char*)malloc(c * sizeof(char)); 
      scanf("%s", pat[i]); 

     } 


     brk_flag2 = 0; 
     found = 0; 
     for (i = 0; i < R; i++) { 

      for (j = 0; j < C; j++) { 

       if (arr[i][j] == pat[0][0]) { 

        if (i + r > R || j + c > C) 
         continue; 

        x = 0; 
        y = 0; 
        brk_flag = 0; 
        for (m = i; m< i + r; m++) { 

         y = 0; 
         for (n = j; n< j + c; n++) { 

          if (arr[m][n] == pat[x][y]) { 

           count++; 
          } 
          else { 

           brk_flag = 1; 
           break; 
          } 
          y++; 
         } 
         if (brk_flag == 1) 
          break; 
         x++; 

        } 

        if (count == (r * c)) { 

         printf("YES\n"); 
         brk_flag2 = 1; 
         found = 1; 
         break; 

        } 
        count = 0; 
       } 

       else 
        continue; 

      } 
      if (brk_flag2 == 1) 
       break; 

     } 

     if (found == 0) { 

      printf("NO\n"); 

     } 

     /* 
     for (i = 0; i < R; i++) { 

      free(arr[i]); 

     } 

     for (i = 0; i < r; i++) { 

      free(pat[i]); 

     } 
     */ 

    } 
    return 0; 
} 

對於模式A大小爲1000 X 1000的測試用例,在Windows上可以正常工作。但在Linux上,我得到一個錯誤,因爲「Abort called」。

我無法找到我在做錯的地方。任何想法,這將是非常讚賞。謝謝。

+0

我應該在末尾明確地設置一個空字符嗎? –

+1

你給你的字符串的'malloc'參數加1嗎? 'scanf'會附加一個空字節('\ 0'),所以你需要確保爲它分配空間。 –

+0

爲什麼downvote?任何解釋? –

回答

2

我懷疑你的問題是在這裏:

pat[i] = (char*)malloc(c * sizeof(char)); 
scanf("%s", pat[i]); 

這對於分配字符c需額外終止空字符只是足夠的空間,但沒有。將其更改爲:

pat[i] = (char*)malloc((c+1) * sizeof(char)); 
scanf("%s", pat[i]); 

這樣scanf可以閱讀c人物,仍然有餘地終止null字符。否則,你將寫入已分配的數組,並且會受到未定義的行爲。

當然,arr[i]也是如此。

+0

感謝您的回答。但是,正如我在評論中提到的那樣,這樣做會將執行時間增加到大約4秒,並且我的測試用例失敗,因爲執行時間限制爲1秒。你能否提出任何想法,我可以提高執行速度。 –

+1

嗯,我不認爲分配額外的字節應該會顯着影響運行時,除了算法可能沒有正確運行的內存分配錯誤。 –

+0

我試圖解決這個問題,https://www.hackerrank.com/challenges/the-grid-search。如果在malloc中將大小設置爲c + 1,則會得到超時。 –

相關問題