2017-06-29 5 views
0

だから私はinsertトライにデータをしようとしている、と私のコードは正常に動作します。しかし、私は少し私の挿入機能を変更し、それはもはや動作しませんまた、メモリリークの原因となります。私にとって、insertの両方のバージョンは同じことをしますが、明らかにそうではありません。誰かがなぜ私に説明してくれますか?前もって感謝します。トライにデータを挿入

ここでここで

#include <stdio.h> 
#include <stdbool.h> 
#include <ctype.h> 
#include <stdlib.h> 
#include <string.h> 

#define SIZE 26 

#define hash(c) (tolower(c) - (int)'a') 

typedef struct node{ 
    bool endWord; 
    struct node* children[SIZE]; 
} node; 

void freeTrie(node* root){ 

    if(root == NULL) return; 

    for (size_t i = 0; i < SIZE; i++) { 
     freeTrie(root->children[i]); 
    } 

    free(root); 
} 

node* newNode(){ 
    node* new = NULL; 

    new = (node*) malloc(sizeof(node)); 

    if(new != NULL){ 

     new->endWord = false; 

     for(int i = 0; i < SIZE; i++) 
      new->children[i] = NULL; 
    } 

    return new; 
} 

void insert(node* root, const char* data){ 

    node* temp = root; 

    for (size_t i = 0, len = strlen(data); i < len; i++) { 

     int index = hash(data[i]); 

     if(temp->children[index] == NULL){ 

      temp->children[index] = newNode(); 

      if (temp->children[index] /*still*/ == NULL){ 
       printf("Something went wrong\n"); 
       return; 
      } 
     } 

     temp = temp->children[index]; 
    } 
    temp->endWord = true; 
} 

bool search(node* root, const char* data){ 

    node* temp = root; 

    for (size_t i = 0, len = strlen(data); i < len; i++) { 

     int index = hash(data[i]); 

     temp = temp->children[index]; 

     if (temp == NULL){ 
      printf("search end here\n"); 
      return false; 
     } 
    } 

    return (temp != NULL && temp->endWord); 
} 

int main() { 

    char data[][8] = {"fox", "foo", "dog", "do"}; 

    node* root = newNode(); 

    if(root == NULL){ 
     printf("Something went wrong\n"); 
     return 1; 
    } 

    for (size_t i = 0, dataSize = sizeof(data)/sizeof(data[0]); i < dataSize; i++) { 
     insert(root, data[i]); 
    } 

    printf("Check: \n"); 

    char output[][32] = {"not found", "found"}; 

    // char s[5]; 
    // fscanf(stdin, "%s", s); 

    printf("%s\n", output[search(root, "fox")]); 

    freeTrie(root); 

    printf("Done\n"); 

    return 0; 
} 

を動作するコードは

void insert(node* root, const char* data){ 

    node* temp = root; 

    for (size_t i = 0, len = strlen(data); i < len; i++) { 

     int index = hash(data[i]); 

     temp = temp->children[index]; 

     if(temp == NULL){ 

      temp = newNode(); 

      if (temp /*still*/ == NULL){ 
       printf("Something went wrong\n"); 
       return; 
      } 
     } 
    } 

    temp->endWord = true; 
} 

私は混乱して作ること insertですPS:私は、私が持っている、CS50xコースの設定の問題のためにこれを行います私のトライに143091語の辞書(アルファベット順)を読み込む。私のプログラムは、スタッフが0.02秒と0.01秒で同じ仕事をしているときには、ロードに約0.1秒、アンロードに0.06秒かかる。私はスタッフのソースコードを見ることは許されていませんが、彼らはデータを格納するためにトライを使用したと思います。より速い実行時間のためにコードを改善するにはどうすればよいですか?配列にデータを格納してからバイナリ検索を行うと高速に実行できますか?

答えて

1

あなたは

temp = temp->children[index]; 

を書くとき、あなたがtempという名前の完全に独立した変数に(私はAそれを呼ぶことにします)temp->children[index]に含まれる値をコピーします。後でtempを変更すると、Aではなく、tempのみが変更されます。つまり、新しいノードはすべてトライに挿入されません。

+0

'temp-> children [index]'がポインタであることを見ると、 'A'はメモリブロック(またはNULL)のアドレスですか?だから、 'temp = temp-> children [index]'の後にtempは 'A'で指定された場所を指しています。私は何かを誤解しましたか? –

+1

@Lone 'temp'は本当に' A'で指定された場所を指します。しかし、後で 'temp'が' NULL'かどうかを確認し、そうであれば、新しいノードを作成し、 'A'がまだ' NULL'を指している間に 'temp'を新しいノードに設定します。最初のバージョンのコードでは、 'A'を修正します。 – yeputons

+0

ああそうです。それは私のために物事を明確にします。どうもありがとうございます。私はあなたにアップフォートを与えることができればいいが、私はできない。 Btw、コードを最適化するためにできることはありますか? –