2017-04-04 113 views
0

对于本实验,我正在研究打印列表时,订单和年龄是正确的,但每个元素的名称均为“退出”。任何想法如何解决这个问题?我知道这是相当长的,但其中一些可能对我的问题至关重要(不知道是哪一个)。学习链接列表

#include <stdio.h> 
#include <string.h> 
#include <stdlib.h> 
typedef struct person { 
    char *name; 
    int age; 
    struct person *next; 
} Person; 

Person *addFront(Person *List, char *Name, int Age) {// add at front, for 
people under 21 

    Person *ptrNew=malloc(sizeof(Person)); 
    ptrNew->name=Name; 
    ptrNew->age=Age; 
    ptrNew->next=List; 
    return ptrNew; 
} 
Person *addRear(Person *List, char *Name, int Age) { // add at rear, for 
people 21 or older 

    Person *ptrNew=malloc(sizeof(Person)); 
    ptrNew->name=Name; 
    ptrNew->age=Age; 
    ptrNew->next=List; 
    if (List==NULL) return ptrNew; 
    Person *ptr; 
    for (ptr=List; ptr != NULL; ptr = ptr->next) { 
      if (ptr->next==NULL) break; 
    } 
    ptr->next=ptrNew; 
    return List; 
} 
void print(Person *List) {    // print the list (name and age for 
each item) 
    Person *ptr; 
    for (ptr=List; ptr != NULL; ptr = ptr->next) { 
      printf("Name:%s Age:%d\n", ptr->name, ptr->age); 
    } 
} 
void printLast(Person *List) {    // print the last person (and 
age) in the list 
    Person *ptr; 
     for (ptr=List; ptr != NULL; ptr = ptr->next) 
      if (ptr->next==NULL) printf("Name:%s Age:%d\n", ptr->name, ptr- 
>age); 
} 
void printFirst(Person *List) {    // print the first person (and 
age) in the list 
    Person *ptr=List; 
    printf("Name:%s Age:%d\n", ptr->name, ptr->age); 
} 
int size(Person *List) {      // return the length of the 
list 
    Person *ptr; 
    int count=0; 
    for (ptr=List; ptr != NULL; ptr = ptr->next) count++; 
    return count; 
} 
int inList(Person *List, char *Name) {   // returns 1 if the name is 
in the list, else 0 
    Person *ptr; 
    for (ptr=List; ptr != NULL; ptr = ptr->next) { 
      if (strcmp(Name, ptr->name)==0) return 1; 
      else return 0; 
    } 

} 
int getAge(Person *List, char *Name) {   // returns the age of the 
person specified 
    Person *ptr; 
    for (ptr=List; ptr != NULL; ptr = ptr->next) { 
      if (strcmp(Name, ptr->name)==0) printf("%d", ptr->age); 
      else return -1; 
    } 

} 
          // return -1 if the person is not in the list 
int main(void) { 
Person *myList = NULL; 
int theAge; 
char theName[128]; 
printf("Enter the name of a person and an age (an integer) : "); 
scanf("%s %d", theName, &theAge); 
while (strcmp(theName, "quit") != 0) { 
    if (theAge < 21) 
     myList = addFront(myList, theName, theAge); 
    else 
     myList = addRear(myList, theName, theAge); 
    printf("Enter another name and age (or \"quit\" and any integer when done) : "); 
    scanf("%s %d", theName, &theAge); 
} 
printf("\n\n\nThe list is "); print(myList); 
printf("\n\nThe list has %d elements\n\n", size(myList)); 
printf("\nThe first person in the list (and their age) is : "); printFirst(myList); 
printf("\nThe last person in the list (and their age) is : "); printLast(myList); 
printf("\n\n"); 
printf("Enter the name of a person (or \"exit\" to exit) : "); 
scanf("%s", theName); 
while (strcmp(theName, "exit") != 0) { 
    if (inList(myList, theName)) 
     printf("\tFound %s (age is %d)\n", theName, getAge(myList, theName)); 
    else 
     printf("\t%s was not found in the list\n", theName); 
    printf("\nEnter the name of a person (or \"exit\" to exit) : "); 
    scanf("%s", theName); 
} 
return 0; 

}

回答

1

addFrontaddRear您使用

ptrNew->name=Name; 

你不能只分配了name指针在列表中,你是从scanf函数读指针。会发生什么事在这种情况下是每List->name将指向相同的位置,如果Name(从scanf函数)的变化(在你的情况下,以“跳槽”作为最后一个元素。每List->name会给“跳槽”

你需要什么做的,是提供一种用于分开每个名称分配内存。

ptrNew->name=malloc(strlen(Name)+1); 
strcpy(ptrNew->name, Name); 

或者,可以改变结构定义为存储阵列中的足够的长度

typedef struct person { 
    char name[20]; 
    int age; 
    struct person *next; 
} Person;  

在这种情况下,可以跳过吨的名称他malloc步骤上面,但strcpy仍然是必需的。

1

您正在使用ptrNew->name作为字符指针,并始终指向theName变量从main()变量。因此链表中的所有节点都指向相同的名称。

相反,你应该在addFront()addRear()更改代码

ptrNew->name= strdup(Name); 

而不是

ptrNew->name=Name; 

确保您free内存适当的时候,你与节点完成。