创建动态链表并打印链表内容。要求通过键盘读入学生的学号和分数,当输入的学号为0时表示链表创建结束,并将读入的学生学号和成绩打印输出。下面程序中存在比较隐蔽的错误,请通过分析和调试程序,发现并改正程序中
时间: 2023-05-31 21:20:16 浏览: 356
### 回答1:
该问题描述的是如何创建动态链表并打印链表内容。要求通过键盘读入学号和成绩,当输入的学号为0时表示链表创建结束,并将读入的学号和成绩打印输出。在程序中存在比较隐蔽的错误,需要通过分析和调试程序,发现并改正错误,并重新运行程序中。
### 回答2:
动态链表是在程序运行期间创建的链表,因此相比较静态链表更加灵活。动态链表的创建是通过一次次分配内存来实现的。每次输入一个学号以及成绩数据,函数就会分配一个新的结点,并将这个结点插入到链表的最后。程序的设计中需要定义一个结构体来存储学号和分数信息。具体实现过程如下:
```c++
#include <iostream>
using namespace std;
struct student
{
int id;
float score;
student* next;
};
int main()
{
student* head = NULL;
student* p = NULL;
do {
int id;
float score;
cout << "请输入学生的学号:" << endl;
cin >> id;
if (id == 0)
{
break;
}
cout << "请输入学生成绩:" << endl;
cin >> score;
student* stu = new student();
stu->id = id;
stu->score = score;
stu->next = NULL;
if (head == NULL)
{
head = stu;
p = head;
}
else
{
p->next = stu;
p = p->next;
}
} while (1);
cout << "学号\t成绩" << endl;
p = head;
while (p != NULL)
{
cout << p->id << "\t" << p->score << endl;
p = p->next;
}
return 0;
}
```
上述代码的错误在于在分配内存(new)之后,忘记赋值给p指针。可以通过定义一个临时指针stp,将分配的内存赋值给此指针,并在p指针之后将临时指针值赋给p。
修改代码如下:
```c++
student* stu = new student();
stu->id = id;
stu->score = score;
stu->next = NULL;
if (head == NULL)
{
head = stu;
p = head;
}
else
{
student* stp = p->next;
p->next = stu;
p = stp;
}
"```
另外值得注意的是,NULL是C/C++中定义的一种空指针常量,其大小为0,可以用来判断指针是否为空。在C++11中也可以使用nullptr代替。需要注意,空指针在使用时需要避免出现未定义行为,例如Dereference( *)以及Subscript中。
以上代码经过正确修改之后,可以实现对学生学号和分数信息的读入、创建以及打印输出。这样,就可以根据实际的需求,在程序中使用动态链表来存储并操作学生信息。
### 回答3:
动态链表是一种常用的数据结构,在实际编程中经常会用到。下面是一个创建动态链表并打印链表内容的程序,我们首先分析一下程序的实现流程:
1. 定义一个结构体节点,节点中保存学生的学号和分数,以及指向下一节点的指针。
2. 初始化链表头节点,定义指向头节点的指针。
3. 依次读入学生的学号和分数,创建节点并插入链表中。当输入的学号为0时表示链表创建结束。
4. 遍历链表,将学生的学号和分数打印出来。
下面是这个程序的代码:
```
#include <stdio.h>
#include <stdlib.h>
struct student { /* 定义学生结构体 */
int num; /* 学号 */
int score; /* 分数 */
struct student* next; /* 指向下一节点的指针 */
};
int main() {
struct student* head, * p, * q;
int num, score;
head = (struct student*)malloc(sizeof(struct student)); /* 初始化头节点 */
head->next = NULL;
q = head;
printf("请输入学生的学号和分数,学号为0表示结束输入:\n");
while (1) {
scanf("%d", &num);
if (num == 0)
break;
scanf("%d", &score);
p = (struct student*)malloc(sizeof(struct student)); /* 创建新节点 */
p->num = num;
p->score = score;
p->next = NULL;
q->next = p; /* 插入新节点 */
q = p;
}
printf("学生学号\t学生分数\n");
printf("-----------------\n");
p = head->next; /* 遍历链表 */
while (p != NULL) {
printf("%d\t%d\n", p->num, p->score);
p = p->next;
}
return 0;
}
```
下面是程序中存在的问题:
1. 对于头节点,程序中没有给予意义。链表的首个节点实则为唯一一个有意义的节点。
2. 程序中有一个内存泄露的bug,每次创建新节点时都要用malloc函数动态分配内存空间,但是在程序结束前并没有释放这些内存空间。
下面是改正后的代码:
```
#include <stdio.h>
#include <stdlib.h>
struct student { /* 定义学生结构体 */
int num; /* 学号 */
int score; /* 分数 */
struct student* next; /* 指向下一节点的指针 */
};
int main() {
struct student* head = NULL, * p, * q;
int num, score;
printf("请输入学生的学号和分数,学号为0表示结束输入:\n");
while (1) {
scanf("%d", &num);
if (num == 0)
break;
scanf("%d", &score);
p = (struct student*)malloc(sizeof(struct student)); /* 创建新节点 */
p->num = num;
p->score = score;
p->next = NULL;
if (head == NULL) { /* 链表为空,将首节点设置为当前节点 */
head = p;
q = head;
}
else {
q->next = p; /* 插入新节点 */
q = p;
}
}
printf("学生学号\t学生分数\n");
printf("-----------------\n");
p = head; /* 遍历链表 */
while (p != NULL) {
printf("%d\t%d\n", p->num, p->score);
q = p;
p = p->next;
free(q); /* 释放节点内存空间 */
}
return 0;
}
```
改正后的代码中修改了两个问题:将头节点去除,改为每次遍历时释放内存空间。这样,程序就能正常运行,并且避免了内存泄露的问题。
阅读全文