我试图做一个程序,从链接列表中插入和删除学生,当我尝试在列表的末尾插入一个学生,但它没有工作。我觉得我的功能算法是正确的,但我仍然。无论如何,这里是代码:
void InsetEnd(){
stud *temp, *newnode;
char n[15];
int a;
printf("Student: \n");
printf("Name: ");
scanf("%s", n);
printf("Age: ");
scanf("%d", &a);
strcpy(newnode->name, n);
newnode->age=a;
temp=head;
while(temp!=NULL){
temp=temp->next;
}
temp = (stud *) malloc (sizeof(stud));
newnode->next = NULL;
temp->next = newnode; }
答案 0 :(得分:0)
对于初学者,指针newnode
具有不确定的值。因此这些陈述
strcpy(newnode->name, n);
newnode->age=a;
导致未定义的行为。
此循环
while(temp!=NULL){
temp=temp->next;
}
没有意义,因为很明显,在循环之后,指针temp
将等于NULL
。
您必须更改列表中的最后一个指针,然后插入新节点。
该函数至少可以通过以下方式查看(尽管使用带有字符数组的函数scanf
,因为它在您的程序中使用是不安全的)
void InsetEnd()
{
stud *newnode;
stud **temp;
char n[15];
int a;
printf("Student: \n");
printf("Name: ");
scanf("%s", n);
printf("Age: ");
scanf("%d", &a);
newnode = ( stud * )malloc( sizeof( stud ) );
strcpy( newnode->name, n );
newnode->age = a;
newnode->next = NULL;
temp = &head;
while ( *temp != NULL ) temp = &( *temp )->next;
*temp = newnode;
}
答案 1 :(得分:0)
我能够解决问题。它只是函数中的分配位置。我实际上必须在创建节点之前分配内存,如果你反转它不会创建任何东西,它只会显示垃圾。
void InsetEnd(){
stud *temp, *newnode;
char n[15];
int a;
printf("Student: \n");
printf("Name: ");
scanf("%s", n);
printf("Age: ");
scanf("%d", &a);
newnode = (stud *) malloc (sizeof(stud));
strcpy(newnode->name, n);
newnode->age=a;
temp=head;
while(temp->next!=NULL){
temp=temp->next;
}
newnode->next = NULL;
temp->next = newnode; }
答案 2 :(得分:0)
好像你抓住了自己的问题。在尝试访问或设置数据之前分配内存至关重要!我觉得还有一些事情需要提及,以便将来帮助你。
void InsetEnd(stud *head) { // pass head pointer, becomes local pointer so its not overriden
if (!head)
return; // dont do anything if list does not exist
stud *newnode; // no need for tmp anymore
char n[15] = ""; // initialize
int a;
printf("Student: \n");
printf("Name: ");
scanf("%14s", n); // take only 14 chars, leaving the 15th '\0' or you'll have problems reading long names after
printf("Age: ");
scanf("%d", &a);
newnode = calloc(1,sizeof(*newnode)); // use calloc to avoid junk
// ^ type casting a return of void* is not necessary in c
strcpy(newnode->name, n);
newnode->age=a;
while(head->next) // NULL is pretty much false
head=head->next;
// no need to set newnode next to null, its already null from calloc
head->next = newnode;
}
希望这有帮助!
答案 3 :(得分:-1)
我将尝试从以下示例中解释它
#include <iostream>
/* run this program using the console pauser or add your own getch, system("pause") or input loop */
class Node {
public:
double data; // data
Node* next; // pointer
};
class List {
public:
List(void) { head = NULL; } // constructor
~List(void); // destructor
bool IsEmpty() { return head == NULL; } //boş kontrolü
Node* InsertNode(int index, double x); //node ekle
int FindNode(double x); //node bul
int DeleteNode(double x); //node sil
void DisplayList(void); //liste görüntüle
private:
Node* head; //baş kısmı
};
Node* List::InsertNode(int index, double x) {
if (index < 0) return NULL;
int currIndex = 1;
Node* currNode = head;
while (currNode && index > currIndex) {
currNode = currNode->next;
currIndex++;
}
if (index > 0 && currNode == NULL) return NULL;
Node* newNode = new Node;
newNode->data = x;
if (index == 0) {
newNode->next = head;
head = newNode;
}
else{
newNode->next = currNode->next;
currNode->next = newNode;
}
return newNode;
}
int List::FindNode(double x) {
Node* currNode = head;
int currIndex = 1;
while (currNode && currNode->data != x) {
currNode = currNode->next;
currIndex++;
}
if (currNode) return currIndex;
return 0;
}
int List::DeleteNode(double x) {
Node* prevNode = NULL;
Node* currNode = head;
int currIndex = 1;
while (currNode && currNode->data != x) {
prevNode = currNode;
currNode = currNode->next;
currIndex++;
}
if (currNode) {
if (prevNode) {
prevNode->next = currNode->next;
delete currNode;
}
else {
head = currNode->next;
delete currNode;
}
return currIndex;
}
return 0;
}
void List::DisplayList()
{
int num = 0;
Node* currNode = head;
while (currNode != NULL)
{
printf("\n%lf",currNode->data);
currNode = currNode->next;
num++;
}
printf("\nNumber of nodes in the list: %d",num);
}
List::~List(void) {
Node* currNode = head, *nextNode = NULL;
while (currNode != NULL)
{
nextNode = currNode->next;
// destroy the current node
delete currNode;
currNode = nextNode;
}
}
int main(int argc, char** argv) {
List list;
list.InsertNode(0,5.4); //başarılı
list.InsertNode(1,6.5); //başarılı
list.InsertNode(-2,5.5);//başarsız
list.InsertNode(2,10.0);//başarılı
list.DisplayList();
list.DeleteNode(5.4);
list.DisplayList();
return 0;
}
现在编辑节点部分
class Node {
public:
int no;
char name[15];
char surname[15];
int age;
Node* next;
};
并插入功能。流程图为here。
Node* List::InsertNode(int index, int no,char name[15],char surname[15],int age){
if (index < 0) return NULL;
int currIndex = 1;
Node* currNode = head;
while (currNode && index > currIndex) {
currNode = currNode->next;
currIndex++;
}
if (index > 0 && currNode == NULL) return NULL;
Node* newNode = new Node;
newNode->no = no;
strcpy_s(newNode->name, name);
strcpy_s(newNode->surname, surname);
strcpy_s(newNode->age, age);
if (index == 0) {
newNode->next = head;
head = newNode;
}
else {
newNode->next = currNode->next;
currNode->next = newNode;
}
return newNode;
}