第一次数据结构笔记(线性表的基本操作)

第一次数据结构笔记(线性表的基本操作)

我们实际上是使用一维数组来描述线性表的

1. 线性表的顺序存储结构:

#define MAXSIZE  20
typedef int ElemType;
//typedef是自定义类型,在这里就是把ElemType自定义成int,在后面看见ElemType实际上就相当于int
typedet struct
{
     ElemType data[ MAXSIZE ] ;        //这里实际上就是定义了一个int型数组,叫data,大小为MAXSIZE
     int length ;                    
     //length问题:在后面会直接引用线性表L和他的长度length,不要感到迷惑,
     //因为在后面的线性表L实际上是已经赋过初值的了,在赋初值时,每输入一个数据,length就+1,
     //这样就可以用length来描述线性表的长度了
 }SqList  ;
 
 
 

2. 地址计算方法
LOC( ai ) = LOC( a1 ) + ( I - 1 ) * C

3.获得元素

#define  ok  1;
typedef int Status ;    
Status GetElem (Sqlist L ;   int   i   ,   Elemtype   *e)   
//i为查找位置,*e用于返回找到的值,ElemType *e实际上就是定义了一个int型指针;
//为什么用指针*e返回值而不用return?因为我们需要return来返回代码运行结果(ERROR还是OK),
//但是return只能返回一个值,所以我们就需要使用指针来返回我们找到的值
{
   if  (  L.length  == 0 || i < 1 || i  >  L.length) //判断查找位置是否合理
   {
                  return ERROR;
               }
               *e  =  L  . data [  i -  1  ]  ;
               //因为顺序表和数组数据位置始终相差1,虽然是顺序表,但是他的本质其实还是一维数组,所以顺序表中第i个数据实际上就是数组中第i-1个数据。
               return  ok;
 }
 
 

4.插入操作
插入思路:
1.如果插入位置不合理,抛出异常。
2.如果线性表长度等于数组长度,则抛出异常或动态增加数组容量(代码效率会变低)。
3.从最后一个元素开始向前遍历到第 i 个位置,分别将他们都向后移动一个位置。(空出第 i 个位置)
4.将要插入元素填入位置 i 处。
5.线性表长度+1。

//插入操作不需要考虑线性表是否为空,为空也可以插入,但是需要考虑线性表是否达到最大长度
 Status ListInsert  ( SqList  *L ,  int i  , ElemType  e)
 //这里需要对线性表做出改变,且需要将这种改变传回顺序表,
 //所以需要用*L(结构指针)来返回改变的值到顺序表中
 //这里e仅仅起到记录需要插入的元素的作用,不需要返回数值,所以不用指针,用int型数据e
 {
 	int  k;
 	if(L -> length == MAXSIZE)    //判断线性表是否达到数组最大值
 	{
 		return ERROR;
 	}
 	if(  i < 1 ||  i > L->length + 1)
 	//判断插入卫视是否不合理 i<1 或者插入位置 i 大于现阶段线性表长度
 	{
 		return  ERROR;
 	}
 	if(  i <= L ->length)       //当插入位置不在表尾时,如果在表尾,直接length--即可。
	{

		for( k = L -> length - 1;  k >= i-1;  k- -)  
		 //因为我们要插入一个数据,所以需要从最后一位开始向后挪动,给需插入元素留位置。
		 //length-1是因为在这里我们操作的对象实际上时数组,线性表的最后一个数据处于末尾length处,
		 //所以在数组中,最后一个元素就处于length-1;
		{
			L ->data[ k+1 ] = L->data[ k ];
			//将最后一个到第 i 个之前的所有元素向后挪,给需要插入的元素留位置。
		}    
	}
	L ->data[i  -  1]  =  e;       //将新元素插入
	L ->length++;             //线性表长度+1
	return ok;
}

5.删除操作
操作思路:
1.`如果位置不合理(为空表),返回异常
2.取出删除元素。
3.从删除元素位置开始遍历到最后一个元素位置,分别将她们都向前按移动一个位置。
4.表长 - 1.

//删除操作不需要考虑顺序表是否达到最大长度,因为即使达到最大长度,依旧可以删除,但是顺序表不能为空,为空没办法删除,所以需要判断线性表是否为空而不需要判断线性表是否已满
Status ListDelete  (SqList *L, int i, ElemType *e)
//删除操作需要对顺序表L做出改变,且需要将这种改变传回顺序表,所以用结构指针*L
//用指针*e来返回删除的值
{
	int k;
	if ( L->length == 0)//当顺序表不为空时
	{
	return ERROR;
	}
	if  ( i < 1 || i > L-> length)
	//判断查找位置是否合乎情理
	{
		return ERROR;
	}
	*e  =  L->data[ i - 1] ;
	//返回需要删除的第i个数据
	//在线性表中是第i个,在数组中是第i-1个,这里我们的操作对象实际上数组
	if ( i < L -> length )//当删除位置不处于线性表末尾时
	{
		for( k = i; k < L-> length ;  k++)
		//将从第 i 个数据到最后一个数据向前挪动
		{
		L - >data[ k - 1] = L -> data[ k ];
		}
		//后一位向前移
	}
	L-> length - - ;
		 //删除之后线性表长度 - 1
	return OK ;
}

PS:1.最坏的情况如果要插入或者删除的位置时
第一个元素,那就意味着要移动所有的元素,所以时间复杂度时O(n)。
2.最好的情况插入和删除操作刚好在最后一个位置操作,因为不需要移动任何元素,所以此时时间复杂度为O( 1 );

线性顺序存储结构的优缺点:
1。优点:不用为了表示表中元素之间的逻辑关系而增加额外的存储空间。
2.有点:可以快速存取表中任意位置的元素。
3.缺点:插入和删除操作需要移动大量元素。
4.缺点:当线性表长度变化较大时,难以确定存储空间的容量。
5.缺点:容易造成存储空间的碎片(申请空间是一整块一整块的申请的)。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值