-3

プロジェクトに取り組んでいますが、セグメンテーション違反が発生し続け、構造体の値が渡されません。なぜ私の頭がおかしくなっているのかを理解する. 単純なプログラムで問題を見つけようとしましたが、問題は見つかったと思いますが、修正方法がわかりません。

問題は、構造体を「malloc」し、値で渡すと、値が失われることです。後で「無料」を追加すると、セグメンテーション違反が発生します。「malloc()」の前または「free()」の後の値にアクセスしようとしていないので、なぜこれが起こっているのか混乱しています。

問題の簡単なモデルを次に示します。

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

    struct structexample
    {
        int element;
    };

    void initStruct(struct structexample * teststruct, int * number)
    {
        teststruct = malloc(sizeof(struct structexample)); 
        teststruct->element = 10;
        printf("teststruct element is %d in initStruct\n", teststruct->element);
        *number = 5;
    }

    void printtest(struct structexample * teststruct, int * number)
    {
        printf("teststruct element is %d in printtest\n", teststruct->element);
        printf("Number is %d\n", *number);
        free(teststruct);
    }

int main()
{
    int number;
    struct structexample teststruct;
    initStruct(&teststruct, &number);
    printtest(&teststruct, &number);
    printf("teststruct element is %d in main()", teststruct.element);
    return 0;
}

これにより、次が生成されます。

teststruct element is 10 in initStruct
teststruct element is -7967792 in printtest
Number is 5
Segmentation fault

「gcc -Wall -pedantic -ansi」でプログラムをコンパイルしましたが、エラーや警告は表示されません。

「malloc」と「free」をコメントアウトすると、次のように正しく生成されます。

teststruct element is 10 in initStruct
teststruct element is 10 in printtest
Number is 5

「free」のみをコメントアウトして「malloc」をそのままにしておくと、セグメンテーション違反は修正されますが、構造体の値は依然として正しくありません。この単純なプログラムでは、"malloc()" と "free()" は実際には必要ありませんが、より大きなプロジェクトでは必要です。この単純なプログラムでそれらを機能させることができれば、より大きなプログラムを修正できると思います。残念ながら、Google で同様の問題を見つけることができません。

4

3 に答える 3

1

スタックとヒープを混在させています

void initStruct(struct structexample * teststruct, int * number)
 {
     teststruct = malloc(sizeof(struct structexample)); 
     ^ There is no need to use malloc, teststruct is on the stack

 ...

int main()
{
    int number;
    struct structexample teststruct;
    initStruct(&teststruct, &number);
于 2016-02-29T18:17:21.117 に答える
1

free()から行を削除するだけprinttest()で、次のようになります。

void printtest(struct structexample * teststruct, int * number)
{
    printf("teststruct element is %d in printtest\n", teststruct->element);
    printf("Number is %d\n", *number);
}

スタック上にあるメモリを解放しようとしているため、セグメンテーション違反が発生します!!

malloc()行は使用されないため、から削除することもできinitStruct()ます。これは、a にスペースを割り当て、そのstruct structexampleアドレスをに返します。これは、ヒープに割り当てられ、に渡されます。つまり、呼び出しが戻ると失われます。teststructstruct structexample *initStruct()initStruct()

于 2016-02-29T19:40:22.993 に答える