个人主页:平行线也会相交
欢迎 点赞👍 收藏✨ 留言✉ 加关注💓本文由 平行线也会相交 原创
收录于专栏【数据结构】
从今天开始,就正式进入数据结构的大门了,把握机会,好好学习,加油。
本文目录
- 1.线性表
- 2.顺序表的实现
- 概念及结构
- 完整代码
- SeqList.h
- SeqList.c
- test.c
- 3.总结
1.线性表
线性表(linear list)是n个具有相同特性的数据元素的有限序列。线性表是一种在实际中广泛使用的数据结构,常见的线性表:顺序表、链表、栈、队列、字符串…
线性表在逻辑上是线性结构,也就是说连续的一条直线。但是在物理结构上并不一定是连续的,线性表在物理上存储时,通常以数组和链式结构的形式存储。
线性表最经典的两种形式:一种就是数组,另一种就是链表。
2.顺序表的实现
顺表作为最简单的数据结构,作用就是把数据存储起来。比如所我们玩的QQ中的联系人、或者通讯录等等。
概念及结构
顺序表是一段物理地址连续的存储单元依次存储数据元素的线性结构,一般情况下采用数组存储,在数组上完成数据的增删查改。
顺序表一般可以分为:
1.静态顺序表:使用定长数组存储。(即长度是固定的)
2.动态顺序表:使用动态开辟的数组存储。
完整代码
SeqList.h
#pragma once
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
#define N 1000
typedef int SLDataType;
静态顺序表(特点就是如果满了就不让插入) 缺点:给多少合适呢?这个很难确定
给小了不够用,给多了就浪费了
//typedef struct SeqList
//{
// SLDataType a[N];
// int size; //表示数组中存储了多少个数据
//}SL;
//
接口函数---命名风格跟着STL走的,方便后期学习STL
//void SeqListInit(SL* ps);//初始化
//void SeqListPushBack(SL* ps, SLDataType x);//尾插
//void SeqListPopBack(SL* ps);//尾删
//void SeqListPushFront(SL* ps, SLDataType x);//头插
//void SeqListPopFront(SL* ps);//头删
//动态顺序表(特点就是如果满了就不让插入) 缺点:给多少合适呢?这个很难确定
//给小了不够用,给多了就浪费了
typedef struct SeqList
{
SLDataType* a;
int size; //表示数组中存储了多少个数据
int capacity; //数组实际能存数据的空间容量是多大
}SL;
//接口函数---命名风格跟着STL走的,方便后期学习STL
void SeqListPrint(SL* ps);//打印
void SeqListInit(SL* ps);//初始化
void SeqListDestory(SL* ps);//销毁
void SeqListCheckCapacity(SL* ps);
void SeqListPushBack(SL* ps, SLDataType x);//尾插
void SeqListPopBack(SL* ps);//尾删
void SeqListPushFront(SL* ps, SLDataType x);//头插
void SeqListPopFront(SL* ps);//头删
SeqList.c
#pragma once
#include"SeqList.h"
void SeqListPrint(SL* ps)
{
for (int i = 0; i < ps->size; i++)
{
printf("%d ", ps->a[i]);
}
}
void SeqListInit(SL* ps)
{
ps->a = NULL;
ps->size = ps->capacity = 0;
}
void SeqListDestory(SL* ps)//销毁
{
free(ps->a);
ps->a = NULL;
ps->capacity = ps->size = 0;
}
void SeqListCheckCapacity(SL* ps)
{
//如果没有空间或者空间不足,就扩容
if (ps->size == ps->capacity)
{
int newcapacity = ps->capacity == 0 ? 4 : ps->capacity * 2;
SLDataType* tmp = (SLDataType*)realloc(ps->a, newcapacity * sizeof(SLDataType));
if (tmp == NULL)
{
printf("realloc fail\n");
exit(-1);//异常时直接终止程序,而return是直接把这个函数返回
}
//来到这说明空间开辟成功
ps->a = tmp;
ps->capacity = newcapacity;
}
}
void SeqListPushBack(SL* ps, SLDataType x)//头插
{
SeqListCheckCapacity(ps);
ps->a[ps->size] = x;
ps->size++;
}
void SeqListPopBack(SL* ps)//尾删
{
//温柔处理方式
//if (ps->size > 0)
//{
// //ps->a[ps->size - 1] = 0;
// ps->size--;
//}
//爆裂处理方式
assert(ps->size > 0);//条件为真没事,为假的话直接终止程序
ps->size--;
}
void SeqListPushFront(SL* ps, SLDataType x)//头插
{
SeqListCheckCapacity(ps);
//挪动数据
int end = ps->size - 1;
while (end >= 0)
{
ps->a[end + 1] = ps->a[end];
end--;
}
ps->a[0] = x;//注意是头插
ps->size++;
}
void SeqListPopFront(SL* ps)//头删
{
assert(ps->size > 0);
//挪动数据
int begin = 1;
while (begin < ps->size)
{
ps->a[begin - 1] = ps->a[begin];
begin++;
}
ps->size--;
}
test.c
#define _CRT_SECURE_NO_WARNINGS 1
#include"SeqList.h"
void TestSeqList1()
{
SL sl;
SeqListInit(&sl);
SeqListPushBack(&sl, 1);
SeqListPushBack(&sl, 2);
SeqListPushBack(&sl, 3);
SeqListPushBack(&sl, 4);
SeqListPushBack(&sl, 5);
//打印
SeqListPrint(&sl);
SeqListPopBack(&sl);
SeqListPopBack(&sl);
SeqListPopBack(&sl);
SeqListPopBack(&sl);
//SeqListPopBack(&sl);
//SeqListPopBack(&sl);
SeqListPopBack(&sl);
SeqListPrint(&sl);
SeqListPushBack(&sl, 10);
SeqListPushBack(&sl, 20);
SeqListPrint(&sl);
SeqListDestory(&sl);//销毁
}
void TestSeqList2()
{
SL sl;
SeqListInit(&sl);
SeqListPushBack(&sl, 1);
SeqListPushBack(&sl, 2);
SeqListPushBack(&sl, 3);
SeqListPushBack(&sl, 4);
SeqListPushBack(&sl, 5);
SeqListPrint(&sl);
printf("\n");
SeqListPushFront(&sl, 10);
SeqListPushFront(&sl, 20);
SeqListPushFront(&sl, 30);
SeqListPushFront(&sl, 40);
SeqListPrint(&sl);
printf("\n");
SeqListPopFront(&sl);
SeqListPopFront(&sl);
SeqListPrint(&sl);
SeqListDestory(&sl);
}
int main()
{
//TestSeqList1();
TestSeqList2();
return 0;
}
3.总结
说一下学这的建议吧,这块的内容还是比C语言那块稍微上一个档次的,首先要有比较好的C语言基础,才能在学习数据结构的过程中如鱼得水。多敲代码也是一个很重要的一点。勤思考,多理一下这里面的思路以及常见的一些思考方式。再次强调一下,学习的时候一定要思考,而不是在哪里刷时长感动自己。切记,思考思考再思考!!!
好了,就到这把。
再见啦!!!