数据结构学习笔记1——顺序表

知识要点:

1.数据之间的逻辑结构:
   集合结构:数据元素之间没有特别的关系,仅同属相同集合
   线性结构:数据元素之间是一对一的关系
   树形结构:数据元素之间存在一对多的层次关系
   图形结构:数据元素之间是多对多的关系




2.数据之间的物理结构:
   顺序存储结构:数据存放在地址连续的内存单元;
   链式存储结构:数据存放的内存单元不连续,通过保存地址值的方式”连接“在一起;


3.数据结构与算法
   数据结构=个体 + 个体的关系
   算法= 对存储数据的操作

   我们把如何现实中大量而复杂的问题以特定的数据类型和特定的存储结构保存到主存储器中(内存),以及在此基础上为实现某个功能(比如查找、删除相应某个元素,对所有元素进行排序)而执行相应的操作,这个相应的操作也叫算法。


4.算法的复杂度:
   时间复杂度:通常用大O记发表示;


   空间复杂度:可通过程序中定义的变量大小总和来估算;





写代码:


5.顺序表(线性表)的实现:
   顺序表的各种操作:生成、销毁、清空、获取、插入、删除。。。;
   实现可复用的顺序表:最大的特点是往顺序表里存入的值不是某种特定的类型,如int、float、struct等类型,而是各种不同类型的地址;通过操作地址,即可达到操作数据的目的,这也体现了C语言指针的重要性;即加快了顺序表的速度,也节省了空间;

    
代码如下:
SeqList.h

SeqList.h作用:可以对数据进行封装,防止外界的修改!用法很不错;如:这样做后,main函数里无法直接操作 list->length  、list->capacity等;保证了数据的安全性

#ifndef _SEQLIST_H
#define _SEQLIST_H

typedef void SeqList;
typedef void SeqListNode;

SeqList * Create_List(int capacity);

void Destory_List(SeqList * seqlist);

void Clear_List(SeqList * seqlist);

int Get_Length(SeqList * seqlist);

int Get_Capacity(SeqList * seqlist);

int Insert_List(SeqList * seqlist, SeqListNode * seqlistnode, int pos);

SeqListNode * Get_List(SeqList * seqlist,int pos);

SeqListNode * Delete_List(SeqList * seqlist,int pos);

#endif

SeqList.c
#include "SeqList.h"
#include <malloc.h>
#include <stdio.h>
#include <string.h>

typedef unsigned int ListNode;//定义节点类型为unsigned int 为什么是unsingned int? 用来存放各种类型的地址值,保证了地址的正确性;

typedef struct _tag_List
{
<span style="white-space:pre">	</span>int length;
<span style="white-space:pre">	</span>int capacity;
<span style="white-space:pre">	</span>ListNode * node;
}LIST;

/*创建顺序表*/
SeqList * Create_List(int capacity)
{
<span style="white-space:pre">	</span>LIST * list = NULL;
<span style="white-space:pre">	</span>if(capacity >= 0)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>list = (LIST *)malloc(sizeof(LIST) + sizeof(ListNode) * capacity);
<span style="white-space:pre">	</span>}

<span style="white-space:pre">	</span>if(list)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>list->length = 0;
<span style="white-space:pre">		</span>list->capacity = capacity;
<span style="white-space:pre">		</span>list->node = (ListNode *)(list+1);//list加1后指向下一个list(结构体类型),刚好指向list下面的地址,即malloc分配的地址                                                                              //把它转换为(ListNode *)  以后就可通过list->node访问下一个节点的地址值;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>return list;
}

/*销毁顺序表*/
void Destory_List(SeqList * seqlist)
{
<span style="white-space:pre">	</span>free(seqlist);
<span style="white-space:pre">	</span>return ;
}

/*清空顺序表*/
void Clear_List(SeqList * seqlist)
{
<span style="white-space:pre">	</span>LIST * list = (LIST *)seqlist;
<span style="white-space:pre">	</span>if(list)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>list->length = 0;//这里我不确定这样操作行不行?我感觉少了步骤,应该把地址值也清空。。。
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>return ; 
}

/*获取顺序表长度*/
int Get_Length(SeqList * seqlist)
{
<span style="white-space:pre">	</span>int ret = -1;
<span style="white-space:pre">	</span>LIST * list = (LIST *)seqlist;
<span style="white-space:pre">	</span>if(list)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>ret = list->length;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>return ret;
}

/*获取顺序表容量*/
int Get_Capacity(SeqList * seqlist)
{
<span style="white-space:pre">	</span>int ret = -1;
<span style="white-space:pre">	</span>LIST * list = (LIST *)seqlist;
<span style="white-space:pre">	</span>if(list)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>ret = list->capacity;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>return ret;
}

/*插入元素*/
int Insert_List(SeqList * seqlist, SeqListNode * seqlistnode, int pos)
{
<span style="white-space:pre">	</span>int i = 0;
<span style="white-space:pre">	</span>LIST * list = (LIST *)seqlist;
<span style="white-space:pre">	</span>int ret = (list != NULL);
<span style="white-space:pre">	</span>ret = ret && (list->length+1 <= list->capacity);
<span style="white-space:pre">	</span>ret = ret && (0 <= pos);
<span style="white-space:pre">	</span>if(ret)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>if(pos >= list->length) 
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>pos = list->length;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>for(i=list->length; i>pos; i--)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>list->node[i] = list->node[i-1];//这里的算法不错
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>list->node[i] = (ListNode)seqlistnode;
<span style="white-space:pre">	</span>list->length++;
}
<span style="white-space:pre">	</span>return ret;
}

/*获取元素*/
SeqListNode * Get_List(SeqList * seqlist,int pos)
{
<span style="white-space:pre">	</span>SeqListNode * node = NULL;
<span style="white-space:pre">	</span>LIST * list = (LIST *)seqlist;
<span style="white-space:pre">	</span>if(list && (0 <= pos) && (pos < list->length))
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>node = (SeqListNode *)list->node[pos];
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>return node;
}

/*删除元素*/
SeqListNode * Delete_List(SeqList * seqlist,int pos)
{
<span style="white-space:pre">	</span>int i = 0;
<span style="white-space:pre">	</span>SeqListNode * node = NULL;
<span style="white-space:pre">	</span>LIST * list = (LIST *)seqlist;
<span style="white-space:pre">	</span>if(list && (0 <= pos) && (pos < list->length))
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>node = (SeqListNode *)list->node[pos];
<span style="white-space:pre">	</span>for(i=pos+1; i<list->length; i++)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>list->node[i-1] = list->node[i];
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>list->length--;
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>return node;

}

Main.c函数测试:
#include <stdio.h>
#include <stdlib.h>
#include "SeqList.h"

int main(int argc, char *argv[]) 
{
<span style="white-space:pre">	</span>int i = 0;
<span style="white-space:pre">	</span>int j = 1;
<span style="white-space:pre">	</span>int k = 2;
<span style="white-space:pre">	</span>int x = 3;
<span style="white-space:pre">	</span>int y = 4;
<span style="white-space:pre">	</span>int index = 0;
<span style="white-space:pre">	</span>StaticList * list = create_list(10);
<span style="white-space:pre">	</span>insert_list(list,&i,0);
<span style="white-space:pre">	</span>insert_list(list,&j,0);
<span style="white-space:pre">	</span>insert_list(list,&k,0);
<span style="white-space:pre">	</span>insert_list(list,&x,0);
<span style="white-space:pre">	</span>for(index=0; index<get_length(list); index++)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>int * p = (int *)get_listnode(list,index);
<span style="white-space:pre">		</span>printf("%d\n",*p);
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>printf("The length is %d\n",get_length(list));
<span style="white-space:pre">	</span>printf("\n");
<span style="white-space:pre">	</span>while(get_length(list) > 0)
<span style="white-space:pre">	</span>{
<span style="white-space:pre">		</span>int * p = (int *)delete_list(list,0);
<span style="white-space:pre">		</span>printf("%d has been delate\n",*p);
<span style="white-space:pre">	</span>}
<span style="white-space:pre">	</span>printf("The length is %d\n",get_length(list));
<span style="white-space:pre">	</span>destory_list(list);
<span style="white-space:pre">	</span>return 0;
}

欢迎大家提出宝贵的意见,共同进步!





  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值