2016-11-15 30 views
1
Node *addToTree(Node *head, Node *newNode) { 
    if (head == NULL) { 
     head = newNode; 
    } else { 
     if (newNode->price < head->price) { 
      head->left = addToTree(head->left, newNode); 
     } else 
     if (newNode->price > head->price) { 
      head->right = addToTree(head->right, newNode); 
     } else 
     if (newNode->price == head->price) { 
      free(newNode); 
     } 
    } 
    return head; 
} 

Node *getCars(char *name) { 
    FILE *fp; 
    if ((fp = fopen(name, "r")) == NULL) { 
     return NULL; 
    } else { 
     Node *head = NULL; 
     Node *tmp; 
     char delim[2] = "|"; 
     char car[MAXLINELENGTH] = {0}; 
     char *token = NULL; 
     int ch; 
     while (!feof(fp)) { 
      tmp = malloc(sizeof(Node)); 
      tmp->left = tmp->right = NULL; 
      fgets(car, MAXLINELENGTH, fp); 
      token = strtok(car, delim); 
      while (token != NULL) { 
       if (strcmp(token, "model") == 0) { 
        token = strtok(NULL, delim); 
        strcpy(tmp->model, token); 
       } else 
       if (strcmp(token, "make") == 0) { 
        token = strtok(NULL, delim);  
        strcpy(tmp->make, token); 
       } else 
       if (strcmp(token, "price") == 0) { 
        token = strtok(NULL, delim);     
        tmp->price = atoi(token); 
       } else 
       if (strcmp(token, "year") == 0) { 
        token = strtok(NULL, delim);     
        tmp->year = atoi(token); 
       } else 
       if (strcmp(token, "color") == 0) { 
        token = strtok(NULL, delim);  
        strcpy(tmp->color, token); 
       } else 
       if (strcmp(token, "type") == 0) { 
        token = strtok(NULL, delim); 
        if (token == NULL) { 
         break; 
        } 
        strcpy(tmp->type, token); 
       } else 
       if (strcmp(token, "mileage") == 0) { 
        token = strtok(NULL, delim);  
        tmp->mileage = atoi(token); 
       } 
       token = strtok(NULL, delim); 
      } 
      if (check("makes.txt", tmp->make) != 1) { 
       continue; 
      } else 
      if (check("colors.txt", tmp->color) != 1) { 
       continue; 
      } else 
      if (check("types.txt", tmp->type) != 1) { 
       continue; 
      } else { 
       head = addToTree(head, tmp); 
      } 
     } 
     free(tmp); 
     fclose(fp); 
     return head; 
    } 
} 

所以对于一个家庭作业,我应该通过输入文件与汽车10000左右的信息是,型号解析,颜色,型号,价格,行驶里程和年并根据它们的价格将它们输入到BST中,当我运行代码时,它说我在malloc的tmp指针处有274个字节丢失。我只是想知道这是什么解决方案,而且我真的可以解析任何建议/帮助因为我的getCars功能是丑陋的,它也需要大约15秒的时间运行,任何帮助,非常感谢!泄漏的内存,同时创造BST,解析需要援助

+0

变化'而{'来'而(与fgets(汽车,MAXLINELENGTH,FP)){'删除'免费(FEOF(FP)!) (tmp);' – BLUEPIXY

+0

@BLUEPIXY你会不会也知道为什么在valgrind中获得“有条件的跳转取决于未初始化的值”错误?或者你会看到更多的代码? –

+0

'continue;' - >'free(tmp);继续;' – BLUEPIXY

回答

0

有你的代码中的多个问题:

  • while (!feof(fp))永远是错的。阅读:Why is “while (!feof (file))” always wrong?

  • 您应该检查所有属性的缺失值。

  • 当您无法匹配make,color或type时,您不会释放节点。

  • 解析循环后不应释放tmp:它可能已被插入到BST中,如果文件为空,它甚至可能未初始化。

  • 令人惊讶的是,您不会将汽车插入BST而是另一辆汽车的价格相同......您应该更准确地检查重复项。

这里是一个改进版本:

Node *addToTree(Node *head, Node *newNode) { 
    if (head == NULL) { 
     head = newNode; 
    } else { 
     if (newNode->price < head->price) { 
      head->left = addToTree(head->left, newNode); 
     } else 
     if (newNode->price > head->price) { 
      head->right = addToTree(head->right, newNode); 
     } else 
     if (newNode->price == head->price) { 
      free(newNode); 
     } 
    } 
    return head; 
} 

Node *getCars(const char *name) { 
    FILE *fp; 
    if ((fp = fopen(name, "r")) == NULL) { 
     return NULL; 
    } else { 
     Node *head = NULL; 
     char delim[] = "|"; 
     char car[MAXLINELENGTH]; 

     while (fgets(car, sizeof car, fp)) { 
      Node *tmp = malloc(sizeof(Node)); 
      /* initialize all members */ 
      tmp->left = tmp->right = NULL; 
      tmp->model[0] = tmp->make[0] = tmp->color[0] = tmp->type[0] = '\0'; 
      tmp->price = tmp->year = tmp->mileage = 0; 
      char *token = token = strtok(car, delim); 
      while (token != NULL) { 
       if (strcmp(token, "model") == 0) { 
        token = strtok(NULL, delim); 
        if (token == NULL) break; 
        strcpy(tmp->model, token); 
       } else 
       if (strcmp(token, "make") == 0) { 
        token = strtok(NULL, delim);  
        if (token == NULL) break; 
        strcpy(tmp->make, token); 
       } else 
       if (strcmp(token, "price") == 0) { 
        token = strtok(NULL, delim);     
        if (token == NULL) break; 
        tmp->price = atoi(token); 
       } else 
       if (strcmp(token, "year") == 0) { 
        token = strtok(NULL, delim);     
        if (token == NULL) break; 
        tmp->year = atoi(token); 
       } else 
       if (strcmp(token, "color") == 0) { 
        token = strtok(NULL, delim);  
        if (token == NULL) break; 
        strcpy(tmp->color, token); 
       } else 
       if (strcmp(token, "type") == 0) { 
        token = strtok(NULL, delim); 
        if (token == NULL) break; 
        strcpy(tmp->type, token); 
       } else 
       if (strcmp(token, "mileage") == 0) { 
        token = strtok(NULL, delim);  
        if (token == NULL) break; 
        tmp->mileage = atoi(token); 
       } 
       token = strtok(NULL, delim); 
      } 
      if (check("makes.txt", tmp->make) != 1 
      || check("colors.txt", tmp->color) != 1 
      || check("types.txt", tmp->type) != 1) { 
       /* unrecognized make, type or color: discard entry */ 
       free(tmp); 
      } else { 
       head = addToTree(head, tmp); 
      } 
     } 
     fclose(fp); 
     return head; 
    } 
} 
+0

圣牛非常感谢你,这真是太神奇了。如果我删除的部分,我释放节点,如果价格相同,我会泄漏内存? –

+0

此外,我不能使用calloc,因为我们还没有在我的计算机科学课上了解到,是否可以使用原始的malloc调用tmp? –

+0

在'addToTree'中,您必须将节点插入树中或将其释放,所以您当前不会在那里泄漏内存,我只是想知道是否应该丢弃具有相同价格的汽车或者是否应该拥有同样的品牌,类型和颜色也是如此。我更新了代码,不使用'calloc()':你必须完全初始化节点。 – chqrlie