C语言 链表 头插法

代码(VS2017中运行)

#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
typedef struct student
{
	int num;
	float score;
	struct student *pnext;//*pnext存的是下一个节点的首地址
}stu,*pstu;
//头插法
void list_head_insert(pstu *pphead, pstu *pptail, int i)//*pphead是二级指针,存储头指针的地址;*pptail是二级指针,存储尾指针的地址
{
	pstu pnew;//pnew是新的链表的一级指针
	pnew = (pstu)malloc(sizeof(stu));//pstu也就是struct student*类型;pnew是首地址;malloc是void类型,所以需要强制类型转化
	memset(pnew, 0, sizeof(stu));
	pnew->num=i;//pnew->num是一个整体;访问结构体的num成员,另其值为i
	if (NULL == *pphead)//如果链表为空(第一次循环时链表为空),让头指针指向新节点,尾指针也指向新节点
	{
		*pphead = pnew;
		*pptail = pnew;
	}
	else//如果链表非空
	{
		pnew->pnext = *pphead;//让新节点的pnext成员指向原有链表头*pphead,*pphead存储的是原有链表头的首地址
		*pphead = pnew;//让原有链表头节点*pphead指向新节点pnew
	}
}
//打印
void list_head_print(pstu phead)
{
	while (phead != NULL)
	{
		printf("%d ", phead->num);
		phead = phead->pnext;
	}
}
int main()
{
	int i;
	pstu phead = NULL;//头指针
	pstu ptail = NULL;//尾指针
	//在vs2017中,这里的scanf结束时要输入三遍ctrl z+三遍回车
	while (scanf("%d", &i) != EOF)
	{
		list_head_insert(&phead, &ptail, i);//&phead是头指针的地址,&ptail是尾指针的地址
	}
	list_head_print(phead);	
	system("pause");
}

运行效果

第一行是输入,最后一行是输出
vs2017的^z^z^z很迷
在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/sinat_42483341/article/details/86547950