【问题标题】:Segmentation fault when adding edge to graph向图形添加边时出现分段错误
【发布时间】:2015-05-28 17:07:52
【问题描述】:

我必须为这个程序使用无向加权图(邻接矩阵)。

typedef struct graph {
  int n;      /* Number of vertices */
  Boolean *visited; /* Will be later used */
  double **mat;  /* It has to be a double */
} Graph;

用于初始化图的函数:

void InitializeGraph(Graph* g, int max)  {
    int i;

    g->visited = malloc(max * sizeof(Boolean));

    g->mat = calloc(max, sizeof(double*));
    for (i = 0; i < max; i++)
        g->mat = calloc(max, sizeof(double));
    g->n = max;
}

现在我只是想在我的图表中添加一条边,但由于某些奇怪的原因它不起作用,我不知道为什么。这是我尝试使用的功能:

void Add(Graph *g, int v1, int v2, double weight){
    g->mat[v1][v2] = weight;
    g->mat[v2][v1] = weight;
}

下面是我的程序如何读取输入以及它如何调用函数 Add()。根据我的测试,读数似乎运行良好。

Graph g;
int i, j, aux;
double daux;

scanf("%d%*c", &aux); /* This is the number of vertices */
InitializeGraph(&g, aux);

for(i = 0; i < g.n; i++){
    for(j = 0; j < g.n; j++){
        scanf("%lf%*c", &daux);
        Add(&g, i, j, daux);
    }
}

在 gdb 上运行程序,结果如下:

(gdb) 运行

启动程序:/home/mintroot/Desktop/media

5

0 5 3 2 2

程序收到信号SIGSEGV,分段错误。

0x00000000004007a4 in Add()

使用此命令行编译程序:

gcc -std=c99 -Wall -pedantic -Werror -o media program.c -lm

我做错了什么,我该如何解决?

【问题讨论】:

  • 什么是g.quant?我在类型定义中没有看到它
  • 我的错,我修好了。应该是 g.n ...我改了名字,因为程序都是葡萄牙语
  • 不用担心,我认为您的问题是嵌套的 for 循环。 mat 仅分配了最大数量的 double* 但在循环的“最后一次”迭代中,您已经超过了尝试访问无效内存的 mat[max][max] 的方式。 (尽管在这种情况下您可能会访问无效内存,但它是最容易看到的)您可能想尝试打印 i 和 j 并查看它有多远。
  • 您可能只想在您的 InitializeGraph 函数中将 g-&gt;mat = calloc(max, sizeof(double*)); 更改为 g-&gt;mat = calloc(max*max, sizeof(double*));
  • 我刚刚尝试打印 i 和 j,它工作正常。他们都没有高于 g.n ...我也尝试更改为 max*max 并且它也没有工作...我完全不知道可能导致问题的原因:\

标签: c graph segmentation-fault graph-theory adjacency-matrix


【解决方案1】:

您的初始化函数正在错误地初始化矩阵:

g->mat = calloc(max, sizeof(double*));
for (i = 0; i < max; i++)
    g->mat = calloc(max, sizeof(double));

请注意,循环的每次迭代都将结果指针记录在相同(错误)的位置:g-&gt;mat。修复它的最快方法是:

g->mat = calloc(max, sizeof(double*));
for (i = 0; i < max; i++)
    g->mat[i] = calloc(max, sizeof(double));

为了它的价值,请注意您的mat 不是二维数组,而是指向一维数组的指针数组。不过,您可以通过与 真正 2D 数组相同的语法访问元素,因此这对您来说可能并不重要。

顺便说一下,@Dave 的道具,他之前发布了然后删除了相同的代码更正。

【讨论】:

  • 谢谢,它成功了。不敢相信我错过了!另外,感谢您对指针数组的提醒,我也将寻求纠正。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-02-19
  • 1970-01-01
相关资源
最近更新 更多