由于昨天上算法课的时候实在无聊,突然想出——能不能用数组来模拟链表,于是经过我的尝试,果真成功了!
思路:
数组和单链表一样,既有数据域又有指针域,而且数组的指针域是固定指向后一个元素的。
那么,头插法就是将数组倒置输入
尾插法就是将数组正常输入
接下看代码:
#include<stdio.h>
#include<stdlib.h>
#define max 100
//用数组模拟单链表
//获取数组长度
int deep(int arr[])
{
int n = 0;
for (int i = 0; i < max; i++)
{
if (arr[i] != NULL)//判断数组,如果数组的元素不为空则让个数自加1
{
n++;
}
}
return n;
}
//插入算法
//思路:得到数组长度,让长度加一位,插入位置后的元素位置后移一位
void insert(int arr[])
{
int n = deep(arr);//获取长度
int pos;
printf("输入你要插入的位置:");
scanf_s("%d", &pos);
if (pos > n)
{
printf("error\n");
}
else
{
int x;
int c_p;//相当于n,为了在后面循环里更加便利进行挪位操作
n += 1;//让数组长度增加一位
arr[n-1] = 0;//让新增加的位置的元素初始化为0
printf("输入你要插入的元素:");
scanf_s("%d", &x);
c_p = n;
for (int i = pos; i <= n; i++)
{
arr[c_p] = arr[c_p-1];//让数组向后挪一位空出要添加的位置
c_p--;
}
arr[c_p] = x;//让我们要添加的位置等于要添加的值
}
}
//遍历打印输出
void print(int arr[])
{
int n = deep(arr);
printf("当前的链表为:\n");
for (int i = 0; i < n; i++)
{
printf("%d\t", arr[i]);
}
printf("\n");
}
//数组元素的删除
//思路:定义pos找到数组要删除的位置,让该位置d 后继元素向前挪一位,即:直接覆盖,最后把最后一位置空
void del(int arr[])
{
int n = deep(arr);
int pos;
printf("输入你要删除的位置:");
scanf_s("%d", &pos);
if (pos > n)
{
printf("error\n");
}
else
{
int c_p = pos;
for (int i = pos; i < n; i++)
{
arr[c_p - 1] = arr[c_p];
c_p++;
}
arr[n - 1] = NULL;
}
}
//数组的清空
//思路:遍历长度后把所有元素置为0
void clear(int arr[])
{
int n = deep(arr);
for (int i = n-1; i >= 0; i--)
{
arr[i] = 0;
}
}
void main()
{
int temp;
int arr[max] = {0};
while (1)
{
printf("************************************单链表************************************\n");
printf("------------------------------------1.头插法建立单链表\n");
printf("------------------------------------2.尾插法建立单链表\n");
printf("------------------------------------3.单链表的插入\n");
printf("------------------------------------4.单链表的删除\n");
printf("------------------------------------5.单链表清空\n");
printf("------------------------------------6.单链表查找\n");
printf("------------------------------------7.获取单链表长度\n");
printf("------------------------------------8.打印单链表\n");
printf("------------------------------------9.exit退出\n");
printf("******************************************************************************\n");
printf("请选择你要做的:\n");
scanf_s("%d", &temp);
if (temp == 9)
{
break;
}
switch (temp)
{
case 1:
{
//头插就是逆序添加元素
int n;
printf("输入你要添加的元素个数:");
scanf_s("%d", &n);
for (int i = n-1; i >= 0; i--)
{
int x;
printf("请输入第%d个元素:", n-i);
scanf_s("%d", &x);
arr[i] = x;
}
printf("链表中的元素为:\n");
for (int i = 0; i < n; i++)
{
printf("%d\t", arr[i]);
}
printf("\n");
break;
}
case 2:
{
//尾插就是正常添加元素
int n;
printf("输入你要添加的元素个数:");
scanf_s("%d", &n);
for (int i = 0; i < n; i++)
{
int x;
printf("请输入第%d个元素:", i+1);
scanf_s("%d", &x);
arr[i] = x;
}
printf("链表中的元素为:\n");
for (int i = 0; i < n; i++)
{
printf("%d\t", arr[i]);
}
printf("\n");
break;
}
case 3:
print(arr);
insert(arr);
print(arr);
printf("\n");
break;
case 4:
print(arr);
del(arr);
print(arr);
printf("\n");
break;
case 5:
print(arr);
clear(arr);
print(arr);
printf("\n");
break;
case 6:
{
int pos;
printf("当前的列表为:\n");
printf("输入你想要查找的位置:");
scanf_s("%d", &pos);
printf("%d\n", arr[pos - 1]);
}
break;
case 7:
printf("链表的长度为:%d", deep(arr));
printf("\n");
break;
case 8:
print(arr);
printf("\n");
break;
default:
printf("程序错误请重新输入");
break;
}
}
printf("程序结束");
}
程序截图: