数据结构
线性:线性表、栈、队列等等
非线性:树(1:N)、图(N:M)等等
存储:顺序存储(arr)、链式存储(*)
线性表:
1、顺序存储的线性表----》arr
2、链式存储的线性表(有头还是无头?)
1、单链表(单向不循环、单向循环)
2、双链表(双向不循环,双向循环)
树(递归思想、非递归思想)
顺序存储线性表:
顺序存储线性表的实现:
sqlist.c文件
#include <stdio.h>
#include <stdlib.h>
#include "sqlist.h"
sqlist *sqlist_create()
{
sqlist *me;
me=malloc(sizeof(*me));
if(me==NULL)
{
return NULL;
}
me->last=-1;
return me;
}
void sqlist_create1(sqlist **ptr)
{
*ptr=malloc(sizeof(**ptr));
if(*ptr==NULL)
{
return ;
}
(*ptr)->last=-1;
return ;
}
int sqlist_insert(sqlist *me,int i,datatype *data)
{
if(me->last==DATASIZE-1)
return -1;
if(i<0 || i>me->last+1)
return -2;
int j;
for(j=me->last;i<=j;j--)
me->data[j+1]=me->data[j];
me->data[i] = *data;
me->last++;
return 0;
}
int sqlist_delete(sqlist *me,int i)
{
int j;
if(i<0||i>me->last)
return -1;
for(j=i+1;j<=me->last;j++)
me->data[j-1]=me->data[j];
me->last--;
}
int sqlist_find(sqlist *me,datatype *data)
{
int i;
if(sqlist_isempty(me)==0)
return -1;
for(i=0;i<=me->last;i++)
{
if(me->data[i]==*data)
return i;
}
return -2;
}
int sqlist_isempty(sqlist *me)
{
if(me->last==-1)
return 0;
return -1;
}
int sqlist_setempty(sqlist *me)
{
me->last=-1;
return 0;
}
int sqlist_getnum(sqlist *me)
{
return (me->last+1);
}
void sqlist_display(sqlist *me)
{
int i;
if(me->last==-1)
return ;
for(i=0;i<= me->last;i++)
{
printf("%d",me->data[i]);
}
printf("\n");
return ;
}
int sqlist_destroy(sqlist *me)
{
free(me);
return 0;
}
int sqlist_union(sqlist *list1,sqlist *list2)
{
int i;
for(i=0;i<=list2->last;i++)
{
if(sqlist_find(list1,&list2->data[i]) < 0)
{
sqlist_insert(list1,0,&list2->data[i]);
}
}
}
sqlist.h文件内容:
#ifndef SQLIST_H__
#define SQLIST_H__
#define DATASIZE 1024
typedef int datatype;
typedef struct node_st
{
datatype data[DATASIZE];
int last;
}sqlist;
sqlist *sqlist_create();
void sqlist_create1(sqlist **);
int sqlist_insert(sqlist *,int i,datatype *);
int sqlist_delete(sqlist *,int i);
int sqlist_find(sqlist *,datatype *);
int sqlist_isempty(sqlist *);
int sqlist_setempty(sqlist *);
int sqlist_getnum(sqlist *);
void sqlist_display(sqlist *);
int sqlist_destroy(sqlist *);
int sqlist_union(sqlist *,sqlist *);
#endif
main.c文件内容:
#include <stdio.h>
#include <stdlib.h>
#include "sqlist.h"
int main()
{
sqlist *list;
datatype arr[]={12,23,34,45,56};
int i,err;
// list=sqlist_create();
sqlist_create1(&list);
if(list == NULL)
{
fprintf(stderr,"sqlist_create fail");
exit(1);
}
for(i=0;i<sizeof(arr)/sizeof(*arr);i++)
if((err=sqlist_insert(list,0,&arr[i]))!=0)
{
if(err==-1)
{
fprintf(stderr,"the arr is full .\n");
}
else if(err==-2)
{
fprintf(stderr,"the pos you want to insert is wrong");
}
else
{
fprintf(stderr,"ERROR");
}
exit(1);
}
sqlist_display(list);
sqlist_delete(list,1);
sqlist_destroy(list);
exit(0);
}
makefile文件内容:
all:mainmain:main.o sqlist.o
$(CC) $^ -o $@
clean:
rm *.o main -rf
链表
有头(先有个头,再有第一个有效结点,第二个有效结点,第三个有效结点……)
无头(没有头,直接就是第一个有效结点,第二个有效结点,第三个有效结点.……)
有头结点的单链表的实现:
list.c文件内容:
#include <stdio.h>
#include <stdlib.h>
#include "list.h"
list * list_create()
{
list *me;
me=malloc(sizeof(*me));
if(me==NULL)
{
return NULL;
}
me->next=NULL;
return me;
}
int list_insert_at(list *me,int i,datatype *data)
{
int j=0;
list *node=me,*newnode;
while(j<i && node!=NULL)
{
node =node->next;
j++;
}
if(node)
{
newnode=malloc(sizeof(*newnode));
if(newnode == NULL)
return -2;
newnode->data=*data;
newnode->next=node->next;
node->next=newnode;
}
else
{
return -3;
}
}
int list_order_insert(list *me,datatype *data)
{
list *p=me,*q;
while(p->next && p->next->data<*data)
{
p=p->next;
}
q=malloc(sizeof(*q));
if(q==NULL)
return -1;
q->data = *data;
q->next=p->next;
p->next=q;
return 0;
}
int list_delete_at(list *me,int i,datatype *data)
{
int j=0;
list *p=me,*q;
*data=-1;
if(i<0)
{
return -1;
}
while(j<i && p)
{
p=p->next;
j++;
}
if(p)
{
q=p->next;
p->next=q->next;
*data = q->data;
free(q);
q=NULL;
return 0;
}
else
{
return -1;
}
}
int list_delete(list *me,datatype *data)
{
list *p=me,*q;
while(p->next && p->next->data!=*data)
{
p=p->next;
}
if(p->next==NULL)
return -1;
else
{
q=p->next;
p->next=q->next;
free(q);
q=NULL;
}
}
int list_isempty(list *me)
{
if(me->next==NULL)
return 0;
return 1;
}
void list_display(list *me)
{
list *node=me->next;
if(list_isempty(me)==0)
return ;
while(node != NULL)
{
printf("%d ",node->data);
node=node->next;
}
printf("\n");
return ;
}
void list_destroy(list *me)
{
list *node,*next;
for(node=me->next;node!=NULL;node=next)
{
next=node->next;
free(node);
}
free(me);
return ;
}
list.h文件内容:
#ifndef LIST_H__
#define LIST_H__
typedef int datatype;
typedef struct node_st
{
datatype data;
struct node_st *next;
}list;
list * list_create();
int list_insert_at(list *,int i,datatype *);
int list_order_insert(list *,datatype *);
int list_delete_at(list *,int i,datatype *);
int list_delete(list *,datatype *);
int list_isempty(list *);
void list_display(list *);
void list_destroy(list *);
#endif
main.c文件内容:
#include <stdio.h>
#include <stdlib.h>
#include "list.h"
int main()
{
list *l;
int i;
datatype arr[]={12,23,45,66,2,9,30};
l=list_create();
if(l==NULL)
{
exit(1);
}
for(i=0;i<sizeof(arr)/sizeof(*arr);i++)
{
if(list_order_insert(l,&arr[i]))
exit(1);
}
list_display(l);
list_destroy(l);
}
makefile文件内容:
all:mainmain:main.o list.o
$(CC) $^ -o $@
clean:
rm *.o main -rf
特点:操作不方便,若是想要查找前面的内容,那么就必须重新开始。
无头结点单链表
这里的插入从头插入。
nohead.c文件内容
#include <stdio.h>
#include <stdlib.h>
#include "nohead.h"
struct node_st *list_insert(struct node_st *list,struct score_st *data)
{
struct node_st *new;
new=malloc(sizeof(*new));
if(new==NULL)
{
return NULL;
}
new->data=*data;
new->next=list;
list=new;
return list;
}
void list_show(struct node_st *list)
{
struct node_st *cur;
for(cur=list;cur!=NULL;cur=cur->next)
{
printf("%d %s %d %d\n",cur->data.id,cur->data.name,cur->data.math,cur- >data.chinese);
}
}
int list_delete(struct node_st **list)
{
struct node_st *cur;
if(*list==NULL)
{
return -1;
}
cur=*list;
*list=(*list)->next;
free(cur);
return 0;
}
struct score_st * list_find(struct node_st *list,int id )
{
struct node_st *cur;
for(cur=list;cur!=NULL;cur=cur->next)
{
if(cur->data.id==id)
{
//printf("%d %s %d %d\n",cur->data.id,cur->data.name,cur->data.math,cur->data.chinese);
return &cur->data;
}
}
return NULL;
}
void list_destroy(struct node_st *list)
{
struct node_st *cur;
if(list == NULL)
{
return ;
}
for(cur=list;cur!=NULL;cur=list)
{
list =cur->next;
free(cur);
}
}
二级指针实现插入:
int list_insert(struct node_st **list,struct score_st *data){
struct node_st *new;
new=malloc(sizeof(*new));
if(new==NULL)
{
return -1;
}
new->data=*data;
new->next=*list;
*list=new;
return list;
}
nohead.h文件内容
#ifndef NOHEAD_H__
#define NOHEAD_H__
#define NAMESIZE 64
struct score_st
{
int id;
char name[NAMESIZE];
int math;
int chinese;
};
struct node_st
{
struct score_st data;
struct node_st *next;
};
struct node_st *list_insert(struct node_st *,struct score_st *data);
void list_show(struct node_st *);
int list_delete(struct node_st **list);
struct score_st * list_find(struct node_st *,int id);
void list_destroy(struct node_st *);
#endif
main.c文件内容
#include <stdio.h>#include <stdlib.h>
#include "nohead.h"
int main()
{
struct score_st *ptr;
struct node_st *list=NULL;
struct score_st tmp;
int i;
for(i=0;i<7;i++)
{
tmp.id=i;
snprintf(tmp.name,NAMESIZE,"stu%d",i);
tmp.math=rand() % 100;
tmp.chinese=rand() % 100;
list=list_insert(list,&tmp);
}
list_show(list);
printf("\n \n");
// list_delete(&list);
// list_show(list);
int id=3;
ptr=list_find(list,id);
if(ptr==NULL)
{
printf("Can not find the message");
}
else
printf("%d %s %d %d \n",ptr->id,ptr->name,ptr->math,ptr->chinese);
list_destroy(list);
exit(0);
}
makefile文件内容
all:mainmain:main.o nohead.o
$(CC) $^ -o $@
clean:
rm *.o main -rf
多项式合并(单链表实现)
#include <stdio.h>#include <stdlib.h>
struct node_st
{
int coef;
int exp;
struct node_st *next;
};
struct node_st *poly_create(int a[][2],int n)
{
int i;
struct node_st *me;
struct node_st *newnode,*cur;
me=malloc(sizeof(*me));
if(me==NULL)
{
return NULL;
}
me->next=NULL;
cur=me;
for(i=0;i<n;i++)
{
newnode=malloc(sizeof(*newnode));
if(newnode==NULL)
return NULL;
newnode->coef=a[i][0];
newnode->exp=a[i][1];
newnode->next=NULL;
cur->next=newnode;
cur=newnode;
}
return me;
}
void poly_show(struct node_st *me)
{
struct node_st *cur;
for(cur=me->next; cur!=NULL; cur=cur->next)
{
printf("(%d %d)",cur->coef,cur->exp);
}
printf(" \n ");
}
void poly_union(struct node_st *p1,struct node_st *p2)
{
struct node_st *p,*q,*r;
p=p1->next;
q=p2->next;
r=p1;
while(p&&q)
{
if(p->exp < q->exp)
{
r->next=p;
r=p;
p=p->next;
}
else if(p->exp > q->exp)
{
r->next=q;
r=q;
q=q->next;
}
else
{
p->coef+=q->coef;
if(p->coef)
{
r->next=p;
r=p;
}
p=p->next;
q=q->next;
}
}
if(p==NULL)
{
r->next=q;
}
else
{
r->next=p;
}
}
int main()
{
int a[][2]={{5,0},{2,1},{8,8},{3,16}};
int b[][2]={{6,1},{16,6},{-8,8}};
struct node_st *p1;
struct node_st *p2;
p1=poly_create(a,4);
p2=poly_create(b,3);
poly_show(p1);
poly_show(p2);
poly_union(p1,p2);
poly_show(p1);
exit(0);
}
约瑟夫算法:
假设要数的数是3,那么从1开始顺时钟,就可以得到顺序3615284(最后剩下7)
利用无头的单项循环链表实现:
创建思路一:
将所有结点都创建好,然后1指向2,2指向3,……最后7指向8;
创建思路二:
先创建好一个,然后指向自己,在创建一个后,上一个指向新创建的,而新创建的指向第一个创建好的。
使用思路二:在任何时刻都是循环的结构
#include <stdio.h>
#include <stdlib.h>
#define JOSE_NUM 8
struct node_st
{
int data;
struct node_st *next;
};
struct node_st *jose_create(int n)
{
int i=1;
struct node_st *me;
struct node_st *newnode,*cur;
me=malloc(sizeof(*me));
if(me==NULL)
return NULL;
me->data=i;
me->next=me;
i++;
cur=me;
for(;i<=n;i++)
{
newnode=malloc(sizeof(*newnode));
if(newnode==NULL)
return NULL;
newnode->data=i;
newnode->next=me;
cur->next=newnode;
cur=newnode;
}
return me;
}
void jose_show(struct node_st *me)
{
struct node_st *list;
for(list=me;list->next!=me;list=list->next)
{
printf("%d ",list->data);
}
printf("%d \n",list->data);
}
void jose_kill(struct node_st **me,int n)
{
struct node_st *cur=*me,*node;
int i=1;
while(cur!=cur->next)
{
while(i<n)
{
node=cur;
cur=cur->next;
i++;
}
printf("%d ",cur->data);
node->next=cur->next;
free(cur);
cur=node->next;
i=1;
}
*me=cur;
printf("\n ");
}
int main()
{
struct node_st *list;
int n=3;
list = jose_create(JOSE_NUM);
jose_show(list);
jose_kill(&list,n);
jose_show(list);
exit(0);
}