在进行算法分析时,语句总的执行次数T(n)是关于问题规模n的函数,进而分析T(n)随n的变化情况并确定T(n)的数量级。算法的时间复杂度,也就是算法的时间量度,记作:T(n)=O(f(n))。他比奥斯随问题规模n的增大,算法执行时间的增长率和f(n)的增长率相同,称作算法的渐进时间复杂度,简称为时间复杂度。其中f(n)是问题规模n的某个函数。
定义:算法的空间复杂度通过计算算法所需的存储空间实现,算法的空间复杂度的计算公式记作:S(n)=O(f(n)),其中,n为问题的规模,f(n)为语句关于n所占存储空间的函数
由零个或多个数据元素组成的有限序列
是一组性质相同的值的集合及定义在此集合上的一些操作的总称
定义:是指一个数学模型及定义在该模型上的一组操作
数据类型抽象:是指抽取出事物具有的普遍性的本质。他要求抽出问题的特征而忽略非本质的细节,是对具体事物的一个概括。抽象是一种思考问题的方式,隐藏了繁杂的细节。
说明
格式:
ADT //抽象数据类型名
Data
//数据元素之间逻辑关系的定义
Operation
//操作
endADT
抽象数据类型定义
ADT 线性表
Data
数据对象(每个元素的类型均为DataType)
Operation
Initlist(*L):初始化操作,建立一个空的线性表L
ListEmpty(L):判断线性表是否为空表,若线性表为空,返回true,否则返回false
ClearList(*L):将线性表清空
GetElem(L,i,*e):将线性表中的第i个未知元素值返回给e
LOcateElem(L,e):在线性表L中查找与给定值e相等的元素,如果查找成功,返回该元素在表中序号表示成功;否则返回0表示失败
ListInsert(*L,i,e):在线性表L中第i个位置插入新元素e
ListDelete(*L,i,*e):删除线性表中第i个位置元素,并用e返回其值
ListLength(L):返回线性表L的元素个数
endADT
对于不同的应用,线性表的基本操作是不同的,上述操作是最基本的,对于实际问题中涉及的关于线性表的更复杂操作,完全可以用这些基本操作的组合实现。
线性表实现集合的并集
void unionL(List *La, list Lb)
int La_len,Lb_len,i ;
ElemType e;
La_len = ListLength(*La);
Lb_len = ListLength(lb);
for(i=1; i<=Lb_len; i++){
GetElem(Lb,i,&e);
if( !LocateElem(La,++La_len,e);
}
}
物理上的存储方式实际上就是在内存中找个初始地址,然后通过占位的形式,把一定的内存空间给占了,然后把相同的数据类型的数据元素依次放在这块空地中
结构代码
#define MAXSIZE 20
typedef int ElemType;
typedef struct
{
ElenmType data[MAXSIZE];
int length; //线性表长度
}SqList;
ElemType是通用数据类型这里是整型
顺序存储结构封装的三个属性
注意:数组的长度与线性表的当前长度需要区分:数组长度是存放线性表的存储空间的总长度,一般初始化后不变。而线性表的当前长度是线性表中元素的个数,是会变化的。
地址计算方法:LOC(ai)=LOC(a1)+(i-1)*c
备注:可以随时计算出线性表中任意位置的地址,所以时间相同,存储时间性能都为O(1),我们通常称为随机存储结构
#define OK 1
#define ERROR 0
#define TRUE 1
#define FALSE 0
typedef int Status;
//Status是函数的类型,其值是函数结果状态代码,如OK等
//初始条件:顺序线性表L已存在,1 <=ListLength(L)
//操作结果:用e返回L中第i个数据元素的值
Status GetElem(SqList L,int i, ElemType *e){
if(L.length==0 || i<1 || i>L.length){
return ERROR;
}
*e = L.data(i-1);
return OK;
}
注意:返回值类型Status是一个整型,约定返回1代表OK,返回0代表ERROR
Status ListInsert(SqList *L,int i, ElemType e)
{
int k;
if(L->length == MAXSIZE)//顺序线性表已经满了
{
return ERROR;
}
if(i<1 || i>L->lengh+1)//当i不在范围内时
{
return ERROR;
}
if(i <= L->length)//若插入数据位置不在表尾
{
//将要插入位置后的数据元素向后移动一位
for( k=L->length-1; k>=i-1;k--)
{
L->data[k+1] = L->data[k];
}
}
L->data[i-1] =e;//将新元素插入
L->length++;
return OK;
}
Status ListDelete(Sqlist *L,int i,ElemType *e)
{
int k;
if(L->length ==0){
return ERROR;
}
if( i<1 || i>L->length+1)//如果删除元素位置超出数组范围,返回ERROR
{
return ERROR;
}
*e = L->data[i-1];
if(i < L->length){
for(k=i ; klength ; k++){
L->data[k-1]=L->data[k];
}
}
L->length--;
return OK;
}
typedef struct Node
{
ElemType data; //数据域
struct Node* Next; //指针域
}Node;
typedef struct Node* LinkList;
思路
代码实现
Status GetElem (LinkList L,int i,ElemType *e)
{
int j;
LinkList p;
p = L->next;
j = 1;
while(p && j<i)
{
return ERROR;
}
*e = p->data;
return OK;
}
Status ListInsert(LinkList *L,int i,ElemType e)
{
int j;
LinkList p,s;
p = *L;
j = 1;
while( p && j<i)//用于寻找i结点
{
p = p->next;
j++;
}
if( !p || j>i)
{
return ERROR;
}
s = (LinkList)malloc(sizeof(Node));
s->data = e;
s->next = p->next;//不能调换顺序
p->next = s;
return OK;
}
Status ListDelete (LinkList *L,int i, ElemType *e)
{
int j;
LinkList p,q;
p=*L;
j=1;
while(p->next && j<i)
{
p=p->next;
++j;
}
if(!(p->next) || j>i)
{
return ERROR;
}
q = p->next;
p->next = q->next;
*e = q->data;
free(q);
return OK;
}
从一个空表开始,生成新结点,读取数据存放到新结点的数据域中,然后将新结点插入到当前链表的表头上,直到结束为止
简单说,就是把新加进的元素放在表头后的第一个位置:
简单说就是现实中插队的现象
void CreaatListHead(LinkList *L,int n)
{
LinkList p;
int i;
srand(time(0));//初始化随机种子
*L = (LinkList)malloc(sizeof(Node));
(*L)->next = NULL;
for( i=0; i<n; i++)
{
p = (LinkList)malloc(sizeeof(Node));
p->data = rand()%100+1;
p->next = (*L)->next;
(*L)->next = p;
}
}
把新结点插入到最后
void CreateListTail(LinkList *L,int n)
{
LinkList p,r;
int i;
srand(time(0));
*L = (LinkList)malloc(sizeof(Node));
r = *L;
for( i=0;i<n;i++)
{
p=(Node *)malloc(sizeof(Node));
p->data = rand()%100+1;
r->next = p;
r = p;
}
r->next = NULL;
}
声明结点p和q
将第一个结点赋值给p,下一结点赋值给q
循环执行释放p和将q赋值给p的操作
Status ClearList(LinkList *L)
{
LinkList p,q;
p = (*L)->next;
while(p)
{
q = p->next;
free(p);
p=q;
}
(*L)->next = NULL;
return OK;
}
线性表需要频繁查找,很少进行插入和删除操作时,宜采用顺序存储结构
需要频繁插入和删除时,宜采用单链表结构
#define MAXSIZE 1000
typedef struct
{
ElemType data;
int cur;
}Component,StaticLinkList[MAXSIZE];
Status InitList(StatusLinkList space)
{
int i;
for( i=0;i<MAXSZIZE-1;i++)
space[i].cur = i+1;
space[MAXSIZE-1].cur = 0;
return OK;
}