【问题标题】:Segmentation fault/Dev C crashing分段错误/Dev C 崩溃
【发布时间】:2014-04-12 16:35:45
【问题描述】:

大家好,我正在尝试做作业,但我整天都找不到程序中的致命错误。让我解释一下: 首先,你给出行数,col 然后是数组的单元格(只有“.”代表空闲空间,“*”代表地雷,都在一行中,没有空格)然后崩溃发生。

main(){
    int  i,col,row,count,N,M,j;
    char **p;
    printf("Give number of rows\n");
    scanf("%d",&N);
    printf("Give number of columns\n");
    scanf("%d\n",&M);
    p=malloc(N*sizeof(char *));   //Saving room for the array
    if (p==NULL)
        return -1;
    for (i=0;i < N ; ++i){
        p[i] = malloc (M * sizeof(char));
        if (*(p+i) == NULL)
            return -1;
    }
    for (i=0; i< N;++i){
        for ( j = 0 ; j < M ;++j)
            scanf("%c",&p[i][j]); //Insert "*" for mines and the rest with "."
    }
    for (row=1; row<= N;++row){           //Here the things get messy
                for ( col = 1 ; col <= M ;++col){
                    if(p[row][col]=='.'){
                        count = 0 ;
                        if(p[row][col+1]=='*' && col < M)
                            count=count+1;
                        if(p[row][col-1]=='*' && col > 1)
                           count=count+1;
                        if(p[row+1][col]=='*' && row < N)
                            count=count+1;
                        if(p[row-1][col]=='*' && row > 1)
                            count=count+1;
                        if(p[row+1][col+1]=='*' && (row < N && col < M))
                            count=count+1;
                        if(p[row+1][col-1]=='*' && (row < N && col > 1))
                            count=count+1;
                        if(p[row-1][col+1]=='*' && ( row > 1 && col < M))
                            count=count+1;
                        if(p[row-1][col-1]=='*' && ( row > 1 && col > 1))
                            count=count+1;
                        printf("%d ", count);
                    }
                    printf("* ");           
                }
                printf("\n");
    }
    printf("\n");
     for (i=0; i< N;++i){       
                for ( j = 0 ; j < M ;++j)
                        printf("%c ",p[i][j]);
        printf("\n");
     }
    for (i = 0 ; i <N ; ++i)
        free(p[i]);
    free(p);
}

【问题讨论】:

  • 我不确定帮助一个人做作业​​是否合乎道德......老实说,所有真正的程序员都通过追踪一个段错误获得了他们的第一堂宝贵的教训,你可能不应该让人们夺走了你的这个机会
  • 当然可以。 OP 明确表示这是家庭作业,说明了问题,并表现出合理的努力来提供细节。
  • 提供的代码未编译。使用调试器检测问题。根据源代码和描述,我认为问题是array out of bound
  • 我为此苦苦挣扎了 4 个小时,但我找不到解决方案,这就是我最终将其发布在这里的原因。如果我喜欢我的其他作业,我会对其进行调试。
  • 检查scanf的返回值。初始化所有变量。使用大括号 {},即使在 if 等之后使用单个语句。之后开始真正寻找错误。

标签: c dev-c++ minesweeper


【解决方案1】:

首先,这是我做的调试(实际上我在代码中看到了问题,只是这样验证,但这对你有用)。

  1. 在文件头部添加#include &lt;stdio.h&gt;#include &lt;stdlib.h&gt;

  2. gcc -Wall -O0 -g x.c -o x 以调试和无优化方式编译。

然后我使用以下在gdb 内运行:

gdb x
...
(gdb) run
Starting program: /home/amb/so/x
warning: no loadable sections found in added symbol-file system-supplied DSO at 0x7ffff7ffa000
Give number of rows
1
Give number of columns
1

.

Program received signal SIGSEGV, Segmentation fault.
0x00000000004007d4 in main () at x.c:25
25                      if(p[row][col]=='.'){
(gdb) print row
$1 = 1
(gdb) print col
$2 = 1
(gdb)

看看它如何在不到 10 秒的时间内告诉我错误在哪里?

你有两个问题:

for (row=1; row<= N;++row){           //Here the things get messy
            for ( col = 1 ; col <= M ;++col){
                if(p[row][col]=='.'){

当您访问p[N][M] 时,SEGV 会出现在这里,但p 的索引只能分别从0N-10M-1。这个循环应该是这样的:

for (row=0; row < N;++row){           //Here the things get messy
            for ( col = 0 ; col < M ;++col){
                if(p[row][col]=='.'){

(注意更改为从row=0 开始,row &lt; N 而不是row &lt;= Mcol 也是如此)。

你遇到的第二个问题是在边缘做什么:

这样的行:

if (p[row][col-1]=='*' && col > 1)
   count=count+1;

应该具有col &gt; 1 条件first,因此除非条件为真,否则它们不会评估数组元素。另外,当col 变成0..M-1,你想要

if ((col > 0) && (p[row][col-1]=='*'))
    count=count+1;

请注意,为了避免歧义,我已将括号括起来。

查看其他边缘时也是如此:

if (p[row][col+1]=='*' && col < M)
    count=count+1;

应该是:

if ((col < M-1) && (p[row][col+1]=='*'))
    count=count+1;

这应该会让你继续前进。但是学会使用调试器

【讨论】:

  • 感谢您的长帖 :) 在您的 cmets 运行顺利之后!嗯,老师说他将在下一课教我们关于 dbg 的知识,所以我没有费心在网上搜索。从一开始我正在用随机 printf >.
  • 投票支持这个真棒,并希望人们在适当的情况下将未来的 c“家庭作业”问题链接到这篇文章。请原谅我只在主帖中发表评论,而不是花时间想出这样的答案。另外我希望这可以作为调试器的一个很好的简单教程,这样人们就可以减少使用 SO 作为家庭作业的答题机
  • 只是在这篇出色的帖子中强调一点,以防 OP 错过它;您必须注意编译器警告,因为如果您的代码有问题,通常编译器会给您提示。您发布的代码应该会发出关于 printfmalloc 未声明的警告(后者特别严重)。
  • @MattMcNabb 据我记得在 dev-c 上没有警告。但是,没有在 linux 上检查。
猜你喜欢
  • 1970-01-01
  • 2012-07-01
  • 2014-04-26
  • 2017-09-28
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-12-11
相关资源
最近更新 更多