C 按相反顺序读取输入
我是C语言的新手。我刚刚学习了指针和C 按相反顺序读取输入,c,C,我是C语言的新手。我刚刚学习了指针和struct。我怎样才能做到呢 #include <stdio.h> #include <stdlib.h> #include <string.h> #include <ctype.h> #define MAX_LINE_LENGTH 80 // The longest line this program will accept #define MAX_NUM_STUDENTS 500 // T
struct
。我怎样才能做到呢
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#define MAX_LINE_LENGTH 80 // The longest line this program will accept
#define MAX_NUM_STUDENTS 500 // The maximum number of students this program can handle
#define MAX_NAME_SIZE 50 // The maximum allowable name length
typedef struct student_s Student;
struct student_s {
char name[MAX_NAME_SIZE];
int age;
Student* next; // Pointer to next student in a list
};
Student studentPool[MAX_NUM_STUDENTS]; // The student pool
int firstFree = 0;
Student* newStudent(const char* name, int age)
{
Student* student = NULL;
if (firstFree < MAX_NUM_STUDENTS) {
student = &studentPool[firstFree];
firstFree += 1;
strncpy(student->name, name, MAX_NAME_SIZE);
student->name[MAX_NAME_SIZE - 1] = '\0'; // Make sure it's terminated
student->age = age;
student->next = NULL;
}
return student;
}
Student* readOneStudent(FILE* file)
{
char buffer[MAX_LINE_LENGTH]; // Buffer into which we read a line from stdin
Student* student = NULL; // Pointer to a student record from the pool
// Read a line, extract name and age
char* inputLine = fgets(buffer, MAX_LINE_LENGTH, file);
if (inputLine != NULL) { // Proceed only if we read something
char* commaPos = strchr(buffer, ',');
if (commaPos != NULL) {
int age = atoi(commaPos + 1);
*commaPos = '\0'; // null-terminate the name
student = newStudent(buffer, age);
}
}
return student;
}
Student* readStudents(FILE *file)
{
Student* first = NULL; // Pointer to the first student in the list
Student* last = NULL; // Pointer to the last student in the list
Student* student = readOneStudent(file);
while (student != NULL) {
if (first == NULL) {
first = last = student; // Empty list case
} else {
last->next = student;
last = student;
}
student = readOneStudent(file);
}
return first;
}
void printOneStudent(Student student)
{
printf("%s (%d)\n", student.name, student.age);
}
void printStudents(const Student* student)
{
while (student != NULL) {
printOneStudent(*student);
student = student->next;
}
}
int main(void)
{
FILE* inputFile = fopen("studlist.txt", "r");
if (inputFile == NULL) {
fprintf(stderr, "File not found\n");
} else {
Student* studentList = readStudents(inputFile);
printStudents(studentList);
}
}
#包括
#包括
#包括
#包括
#定义最大行长80//此程序将接受的最长行
#定义MAX_NUM_STUDENTS 500//此程序可以处理的最大学生数
#定义最大名称大小50//允许的最大名称长度
类型定义结构学生的学生;
结构学生{
字符名称[最大名称大小];
智力年龄;
Student*next;//指向列表中下一个学生的指针
};
学生池[最大学生人数];//学生池
int firstFree=0;
学生*新闻学生(常量字符*姓名,整数)
{
Student*Student=NULL;
如果(第一次免费<最大学生人数){
学生=&studentPool[firstFree];
firstFree+=1;
strncpy(学生->姓名、姓名、最大姓名大小);
student->name[MAX\u name\u SIZE-1]='\0';//确保它已终止
学生->年龄=年龄;
学生->下一步=空;
}
留学生;
}
学生*readOneStudent(文件*FILE)
{
char buffer[MAX_LINE_LENGTH];//我们从stdin中读取一行的缓冲区
Student*Student=NULL;//指向池中学生记录的指针
//读一行,提取姓名和年龄
char*inputLine=fgets(缓冲区、最大行长度、文件);
如果(inputLine!=NULL){//仅当我们读取某些内容时才继续
char*commaPos=strchr(缓冲区“,”);
如果(逗号!=NULL){
int age=atoi(逗号+1);
*逗号='\0';//null终止名称
学生=新学生(缓冲区、年龄);
}
}
留学生;
}
学生*readStudents(文件*FILE)
{
Student*first=NULL;//指向列表中第一个学生的指针
Student*last=NULL;//指向列表中最后一个学生的指针
学生*Student=readOneStudent(文件);
while(学生!=NULL){
if(first==NULL){
first=last=student;//列表大小写为空
}否则{
最后->下一个=学生;
最后=学生;
}
学生=readOneStudent(文件);
}
先返回;
}
无效printOneStudent(学生)
{
printf(“%s(%d)\n”,student.name,student.age);
}
无效打印学生(常量学生*学生)
{
while(学生!=NULL){
printOneStudent(*学生);
学生=学生->下一步;
}
}
内部主(空)
{
FILE*inputFile=fopen(“studlist.txt”、“r”);
if(inputFile==NULL){
fprintf(stderr,“未找到文件”\n);
}否则{
学生*studentList=readStudents(输入文件);
打印学生(学生名单);
}
}
您当前要在(非空列表的)末尾插入此代码:
要在非空列表的前面插入,只需每次将新学员设置为第一个学员,方法是将其next
指针指向当前first
学员,并将first
指针指向新学员
if (first == NULL) {
first = last = student; // Empty list case
} else {
student->next = first;
first = student;
}
画盒子;用箭头将它们连接起来。这应该变得显而易见
此外,您可以简单地使用:
student->next = first;
first = student;
如果
first
为空,student->next
将(重新)设置为空,因此无需在first
上使用特殊情况。由于last
仅在添加到列表末尾的函数中使用,因此在前面插入时,根本不需要last
。这两个观察结果使代码比建议的第一个版本更简单。您当前有此代码要插入(非空列表的)末尾:
要在非空列表的前面插入,只需每次将新学员设置为第一个学员,方法是将其next
指针指向当前first
学员,并将first
指针指向新学员
if (first == NULL) {
first = last = student; // Empty list case
} else {
student->next = first;
first = student;
}
画盒子;用箭头将它们连接起来。这应该变得显而易见
此外,您可以简单地使用:
student->next = first;
first = student;
如果
first
为空,student->next
将(重新)设置为空,因此无需在first
上使用特殊情况。由于last
仅在添加到列表末尾的函数中使用,因此在前面插入时,根本不需要last
。这两个观察结果使代码比建议的第一个版本更简单。在前面插入通常非常容易。很难在结尾插入。这与任何老师可能会给一个班级做的关于链表主题的第二个家庭作业惊人地相似。链表问题总是可以用笔、纸、画框和箭头来回答。请说明这是否是一项家庭作业,根据此处描述的折衷方案,您是否需要帮助:为什么不花点时间看看Student*readStudents(FILE*FILE)
中的else
语句,思考一下您需要做些什么来last->next=Student代码>和last=学生
要在列表的开头而不是尾部添加?@DavidC.Rankin根据折衷方案提供了第一个提示(可能是有意的)。请说明您是否想要更多,是否愿意尽自己的一份力量。这不是重复的吗?尽管代码是用Java编写的,但在前面插入通常非常简单。很难在结尾插入。这与任何老师可能会给一个班级做的关于链表主题的第二个家庭作业惊人地相似。链表问题总是可以用笔、纸、画框和箭头来回答。请说明这是否是一项家庭作业,根据此处所述的折衷方案,您是否需要帮助:为什么不花点时间看看