2017-08-04 10 views
-2

mallocを使用しないようにバックネットスタックの一部を編集しようとしています。常に失敗するためです。コードはmallocを使ってオブジェクトを作成し、リンクされたリストに挿入します。次のコードスニペットでは、mallocをコメントアウトしました。私の計画は、構造体のローカルインスタンスを作成し、それを私のリストに挿入することです。私は私のリストに2つの項目を挿入することができる、3番目を追加しようとすると、リストが正しく終了されていないと私は無限のwhileループを入力します。誰でも私のリストが正しく終了していない理由を見ることができますか?Cリンクリスト無限ループ

CHobjectsはstuctであり、それらのリンクリストが必要です。新しいCHobjectインスタンスを作成するためにmallocを使用することはできません。これを回避するために、私はCHobjectのローカルインスタンスを作成し、それを私のリストに追加しようとしています。

CHobjects* newNode(instance, channel, name, description) 
{ 
CHobjects *node; 
CHobjects newNode; 

    node=CHobjects; 
    while(node!=NULL) 
    { 
     if(node->instance==instance) 
      return 
     node=node->next; 
    } 
    if(strlen((char *)objectName)>objectNameMax || strlen((char *)description)>descriptionMax) 
     goto cc8; //fail name or description is too long 
// if((node=(CHobject *)malloc(sizeof(CHobject)))==NULL) //get a block of space for this object's info 
// goto cc8; //fail if we can't get space for it 
    test.next=CHobjects; //link on to list 
    CHobjects=&test; 
    CHcount++; 
} 

このコードでは、要素をリストに追加するだけで、コード全体がデフォルト値に設定されます。

+0

実際のコードを表示してください。 'objectName'はどこに定義されていますか? 'CHobject'はどこに定義されていますか? – lurker

+0

実際のコードを投稿してください。また、 'strlen((char *)objectName)> objectNameMax'と' strlen((char *)objectName-> objectNameMax')は同じに見え、混乱します。 –

+0

整数型を仮定してコンパイルします。 –

答えて

0

あなたの質問は少し不明ですが、とにかく便利な回答を与えることは可能でしょう。

私はあなたがこのリンクリストのストレージとしてアレイを使用しており、プラスとあなたが同時に

#include <stdio.h> 

struct list { 
    int value; 
    struct list *next; 
}; 

static void 
print_list(const struct list *item) 
{ 
    while (item->next != NULL) { 
     fprintf(stdout, "%d\n", item->value); 
     item = item->next; 
    } 
} 

int 
main(void) 
{ 
    struct list items[15]; 
    size_t count; 

    count = sizeof items/sizeof *items - 1; 
    for (int index = 0; index < count; ++index) { 
     items[index].next = &items[index + 1]; 
     items[index].value = index + 1; 
    } 
    items[count].next = NULL; 

    print_list(items); 
} 
を配列し、リンクリストの両方を持つことになります実装できることを考えることができる唯一の方法

ご覧のとおり、格納場所として使用するには、指定した配列要素にアクセスする必要があり、配列はリンクされたリストの有効期間を通じて有効である必要があります。

+0

私は質問をもっと明確にしようとしました。上記のコードは、デフォルト値を設定するだけの他のコードと同様に完全です。私はコード構造を変更することはできませんが、私はmallocの使用を置き換える必要があります。 –

1

コメントで私たちの広範な議論の後、私はそれがあなたが問題がグローバルリストのローカル構造体インスタンスの使用であることは明らかだと思います。スタック上に作成した構造体はnewNode()関数を終了すると無効になり、次の呼び出しで同じスタック領域がリサイクルされます。したがって、同じインスタンスを自分自身にリンクし、2回の呼び出しの後に循環リストを取得し、無限ループに入ります。

明らかにヒープなしのプレーンCであるため、コンパイル時に事前に割り当てられた独自の構造体アロケータをグローバルメモリにロールすることが唯一のチャンスです。すべての割り当て(つまり、リストの最大長)を満たすのに十分な大きさのCHオブジェクトのグローバル配列を宣言します。あなたのケースでは、これはここで生のアウトラインです4.のようだ:

#define CHOBJECTS_MAX 4 

static CHobjects gaCHobjects [CHOBJECTS_MAX]; 
static int giNextSlot = 0; 

public: static CHobjects* Allocator() 
    { 
    return gaCHObjects + giNextSlot++; 
    } 

機能アロケータは()を使用すると、それぞれの呼び出しの新しいインスタンスを取得しますので、あなたのグローバル配列から構造体のポインタを返し、giNextSlotインデックスをインクリメント。このポインタは、ローカルのCHobjectsインスタンスの代わりにnewNode()内で使用してください。