一、数据结构
数据结构:
相互之间存在一种或多种特定关系的元素集合
逻辑结构:
集合: 所以数据在一个集合,关系平等
线性: 数据和数据之间一对一关系
树: 一对多
图: 多对多
物理结构(在内存中的存储关系)
1 顺序存储
顺序存储结构:把数据元素存放在地址连续的存储单元里面,其数据间的逻辑关系和物理关系是一致的.
2 链式存储
链式存储结构:把数据元素存放在任意的存储单元里,这组存储单元可以是连续,也可以是不连续的.
3 索引存储
该方法通常在储存结点信息的同时,还建立附加的索引表。
索引表由若干索引项组成。若每个结点在索引表中都有一个索引项,则该索引表称之为稠密索引(Dense Index)。若一组结点在索引表中只对应一个索引项,则该索引表称为稀疏索引(Spare Index)。索引项的一般形式是: (关键字、地址)
关键字是能唯一标识一个结点的那些数据项。稠密索引中索引项的地址指示结点所在的存储位置;稀疏索引中索引项的地址指示一组结点的起始存储位置。
4 散列存储
该方法的基本思想是:根据结点的关键字直接计算出该结点的存储地址。
四种基本存储方法,既可单独使用,也可组合起来对数据结构进行存储映像。
数据的类型
是一组性质相同的值的集合及定义在此集合上的一些操作总称
原子类型 int char float
结构类型 struct union
算法:
是解决特定问题求解步骤的描述,计算机表现为指令的有限序列,每条指令表示一个或多个操作
算法特征:
- 输入,输出特性,输入时可选的,输出时必须的。
- 有穷性,执行的步骤会自动结束,不能死循环,并且每一步是在可以接受时间内完成
- 确定性 同一个输入,会得到唯一的输出
- 可行性 每一步都是可以实现的
算法的设计:
1.正确性
2.可读性,便于交流,阅读,理解
3.健壮性,输入非法数据,能进行相应的处理,而不是产生异常
4.高效,存储低,效率高
算法时间复杂度:
也就是执行这个算法花费时间的度量推到时间复杂度
1.用常数取代运行时间中的所有加法常数
2.在修改后的运行函数中,只保留最高项
3.如果最高项存在且不是1,保留
线性表
零个或多个数据元素的有限序列
元素之间是有顺序的,如果存在多个元素,第一个元素无前驱,最后一个元素没有后继,其他的元素只有一个前驱和后继
当线性表元素的个数n定义为线性表的长度,当n=0时,为空表。
线性:线性表顺序存储的优点,缺点
优点
-
1无需为表中的逻辑关系增加额外存储空间
-
2可以快速随机访问元素O(1)。
缺点
- 插入,删除元素需要移动元素O(N)
- 无法动态存储
线性表的链式存储
解决顺序存储的缺点,插入和删除,动态存储问题。
特点:
1. 线性表链式存储结构的特点是一组任意的存储单位存储线性表的数据元素,存储单位可以是连续,也可以不连续,但默认malloc位置是不连续的。
2.链式结构还需要一个元素存储下一个元素的地址
3.把存储元素信息的域叫数据域,把存储直接后继位置的域叫指针域,这两部分信息组成数据元素的存储映像叫做结点。
查看内存泄漏命令:
Valgrind ./a.out
顺序表和链表的 优缺点
存储方式:
顺序表是一段连续的存储单元
链表是逻辑结构连续物理结构不连续
时间性能
查找
顺序表O(1)
链表O(n)
插入和删除
顺序表O(n)
链表O(1)
空间性能
顺序表 需要预先分配空间 大小固定
链表 动态存储
顺序表代码:
seqlist.h:
#ifndef _SEQLIST_H_
#define _SEQLIST_H_
typedef struct person {
char name[32];
char sex;
int age;
int score;
}DATATYPE;
typedef struct list {
DATATYPE *head;
int tlen;
int clen;
}SeqList;
SeqList *CreateSeqList(int len);
int ShowSeqList(SeqList *list);
int InsertTailSeqList(SeqList *list, DATATYPE *data);
int IsFullSeqList(SeqList *list);
int IsEmptySeqList(SeqList *list);
int InsertPosSeqList(SeqList *list, DATATYPE *data, int pos);
int FindSeqList(SeqList *list, char *name);
int ModifySeqList(SeqList *list, char *old, DATATYPE *newdata);
int DeleteSeqList(SeqList *list, char *name);
int ClearSeqList(SeqList *list);
int DestroySeqList(SeqList *list);
int GerSizeSeqList(SeqList* list);
DATATYPE* GetItemSeqList(SeqList*list,int pos );
#endif
seqlist.c:L
#include "./seqlist.h"
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
SeqList *CreateSeqList(int len)
{
SeqList* sl = (SeqList*) malloc(sizeof(SeqList));
if(NULL == sl)
{
perror("CreateSeqList malloc");
return NULL;
}
sl->head = (DATATYPE*)malloc(sizeof(DATATYPE)*len);
if(NULL == sl->head )
{
perror("create seqlist malloc 2");
return NULL;
}
sl->tlen = len;
sl->clen = 0;
return sl;
}
int InsertTailSeqList(SeqList *list, DATATYPE * data)
{
if(IsFullSeqList(list))
{
return 1;
}
//strcpy memcpy
memcpy(&list->head[list->clen] ,data,sizeof(DATATYPE));
list->clen ++;
return 0 ;
}
int IsFullSeqList(SeqList *list)
{
return list->clen == list->tlen ;
}
int ShowSeqList(SeqList *list)
{
int len = GerSizeSeqList(list);
int i = 0 ;
for(i = 0 ;i<len;i++)
{
printf("%s %c %d %d\n",list->head[i].name,list->head[i].sex,list->head[i].age
, list->head[i].score);
}
return 0;
}
int GerSizeSeqList(SeqList* list)
{
return list->clen ;
}
int IsEmptySeqList(SeqList*list)
{
return 0 == list->clen ;
}
int InsertPosSeqList(SeqList *list, DATATYPE *data, int pos)
{
if(IsFullSeqList(list))
{
return 1;
}
int i = 0 ;
for(i = list->clen;pos< i;i--)
{
list->head[i] = list->head[i-1];
}
memcpy(&list->head[pos],data,sizeof(DATATYPE));
list->clen ++;
return 0;
}
int FindSeqList(SeqList *list, char *name)
{
int len = GerSizeSeqList(list);
int i = 0 ;
for(i = 0;i<len;i++)
{
if(0==strcmp(list->head[i].name ,name))
{
return i;
}
}
return -1;
}
DATATYPE* GetItemSeqList(SeqList*list,int pos )
{
if(pos<0 || pos >=list->clen)
{
return NULL;
}
return &list->head [pos];
}
int ModifySeqList(SeqList *list, char *old, DATATYPE *newdata)
{
int ret = FindSeqList(list,old);
if(-1 == ret)
{
return 1;
}
memcpy(&list->head[ret],newdata,sizeof(DATATYPE));
return 0;
}
int ClearSeqList(SeqList *list)
{
list->clen = 0;
return 0;
}
int DestroySeqList(SeqList *list)
{
free(list->head);
free(list);
return 0;
}
int DeleteSeqList(SeqList *list, char *name)
{
int ret = FindSeqList(list,name);
if(-1== ret)
{
return 1;
}
int i = 0 ;
for(i = ret;i<list->clen;i++)
{
list->head[i] = list->head[i+1];
}
list->clen--;
return 0;
}
链式表代码:
linlkist.h:
#ifndef _DOULINKLIST_H_
#define _DOULINKLIST_H_
typedef struct person {
char name[32];
char sex;
int age;
int score;
}DATATYPE;
typedef enum {FORWARD,BACKWARD}DIRECT;
typedef struct dou_node {
DATATYPE data;
struct dou_node *next,*prev;
}DouLinkNode;
typedef struct list {
DouLinkNode *head;
int clen;
}DouLinkList;
typedef int (*pFun)(DATATYPE*data,void* arg);
DouLinkList *CreateLinkList();
int InsertHeadLinkList(DouLinkList *list, DATATYPE *data);
int ShowLinkList(DouLinkList *list,DIRECT dire);
//DouLinkNode *FindLinkList(DouLinkList *list, char *name);
DouLinkNode *FindLinkList(DouLinkList *list, pFun fun,void *arg);
int InsertTailLinkList(DouLinkList *list, DATATYPE*data);
int InsertPosLinkList(DouLinkList *list, DATATYPE*data,int pos);
int DeleteLinkList(DouLinkList *list, pFun fun,void * arg);
int ModifyLinkList(DouLinkList *list, pFun fun, void* arg,DATATYPE *data);
int DestroyLinkList(DouLinkList *list);
int IsEmptyLinkList(DouLinkList*list);
int GetSizeDouLinkList(DouLinkList *list);
#endif
linklist.c:
#include "DouLinkList.h"
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
DouLinkList *CreateLinkList()
{
DouLinkList* ll = (DouLinkList*)malloc(sizeof(DouLinkList));
if(NULL == ll)
{
perror("CreateLinkList malloc");
return NULL;
}
ll->head = NULL;
ll->clen = 0;
return ll;
}
int InsertHeadLinkList(DouLinkList *list, DATATYPE *data)
{
DouLinkNode* newnode = (DouLinkNode*)malloc(sizeof(DouLinkNode));
if(NULL == newnode)
{
perror("InsertHeadLinkList");
return 1;
}
memcpy(&newnode->data,data,sizeof(DATATYPE));
newnode->next = NULL;
newnode->prev =NULL;
if(NULL == list->head)
{
list->head = newnode;
}
else
{
newnode->next = list->head ;
list->head->prev = newnode;
list->head = newnode;
}
list->clen ++;
return 0;
}
int GetSizeDouLinkList(DouLinkList *list)
{
return list->clen ;
}
int ShowLinkList(DouLinkList *list,DIRECT dire)
{
int len = GetSizeDouLinkList(list);
DouLinkNode * tmp = list->head ;
int i = 0 ;
if(FORWARD == dire)
{
for(i = 0 ;i<len;i++)
{
printf("%s %c %d %d\n",tmp->data.name,tmp->data.sex,tmp->data.age
,tmp->data.score);
//tmp++
tmp= tmp->next ;
}
}
else
{
while(tmp->next)
{
tmp=tmp->next;
}
for(i = 0 ;i<len;i++)
{
printf("%s %c %d %d\n",tmp->data.name,tmp->data.sex,tmp->data.age
,tmp->data.score);
//tmp++
tmp= tmp->prev ;
}
}
return 0;
}
DouLinkNode *FindLinkList(DouLinkList *list, pFun fun,void *arg)
{
int len = GetSizeDouLinkList(list);
DouLinkNode* tmp = list->head ;
int i = 0 ;
for(i = 0 ;i<len;i++)
{
//if(0 == strcmp(tmp->data.name,name))
if(fun(&tmp->data,arg))
{
return tmp;
}
//tmp++;
tmp = tmp->next ;
}
return NULL;
}
int IsEmptyLinkList(DouLinkList*list)
{
return 0 == list->clen ;
}
int InsertTailLinkList(DouLinkList *list, DATATYPE *data)
{
DouLinkNode* tmp = list->head ;
if(IsEmptyLinkList(list))
{
return InsertHeadLinkList(list,data);
}
else
{
DouLinkNode* newnode =(DouLinkNode*) malloc(sizeof(DouLinkNode));
if(NULL == newnode)
{
perror("InsertTailLinkList malloc");
return 1;
}
memcpy(&newnode->data , data,sizeof(DATATYPE));
newnode->next = NULL;
newnode->prev =NULL;
while(tmp->next )
{
tmp =tmp->next;
}
newnode->prev = tmp;
tmp->next = newnode;
}
list->clen ++;
return 0;
}
int InsertPosLinkList(DouLinkList *list, DATATYPE*data,int pos)
{
DouLinkNode* newnode = (DouLinkNode*)malloc(sizeof(DouLinkNode));
if(NULL == newnode)
{
perror("InsertTailLinkList malloc");
return 1;
}
memcpy(&newnode->data ,data,sizeof(DATATYPE));
newnode->next = NULL;
newnode->prev =NULL;
DouLinkNode* tmp = list->head ;
int i = 0 ;
for(i = 0 ;i<pos;i++)
{
tmp = tmp->next ;
}
newnode->next = tmp;
newnode->prev = tmp->prev;
tmp->prev = newnode;
if(newnode->prev)
{
newnode->prev->next = newnode;
}
else
{
list->head = newnode;
}
list->clen ++;
return 0;
}
int DeleteLinkList(DouLinkList *list, pFun fun,void * arg)
{
DouLinkNode* tmp = FindLinkList(list,fun,arg);
if(NULL == tmp)
{
return 1;
}
if(tmp->next )
tmp->next->prev = tmp->prev;
if(tmp->prev)
{
tmp->prev->next = tmp->next;
}
else
{
list->head = tmp->next ;
}
list->clen -- ;
free(tmp);
return 0 ;
}
int ModifyLinkList(DouLinkList *list, pFun fun, void* arg,DATATYPE *data)
{
DouLinkNode* tmp = FindLinkList(list,fun,arg);
if(NULL == tmp)
{
return 1;
}
memcpy(&tmp->data ,data,sizeof(DATATYPE));
return 0;
}
int DestroyLinkList(DouLinkList *list)
{
DouLinkNode* tmp = NULL;
int len = GetSizeDouLinkList(list);
int i = 0 ;
for(i = 0 ;i<len;i++)
{
tmp = list->head ;
list->head = list->head->next ;
free(tmp);
}
free(list);
return 0;
}