线性表详解(c语言版)

放假回家第三天,接着复习。啦啦啦:
1. 线性表:线性表是最常用且最简单的一种数据结构,一个线性表就是若干个数据元素的有限序列。
线性表的操作:
InitList(&L)构造一个空的线性表
DestroyList(&L)销毁线性表
ClearList(&L)清空线性表
ListEmpty(L) 判断线性表是否为空
ListLength(L)获取线性表的长度
GetElem(L,i,&e)获取线性表L中的第i个元素,返回结果保存在e中
ListInsert(&L,i,e)向线性表L中第i-1个位置插入元素e
ListDelete(&L,i,&e)将线性表L中第i个位置的元素,并用e返回其值
2. 线性表的实现方式:

  • 顺序线性表:数据元素按顺序依次排列,在存储空间的位置为连续的存储区域,优点是便于存取,能根据下标获取相应的元素,缺点是必须有连续的存储空间(可以按数组理解)。

  • 链式线性表 (单链表):数据元素依次排列,每一个数据元素中都含有指向下一个元素的指针,通过指针来将所有的元素连接在一起形成线性表。优点是可以充分的利用碎片化的存储空间,不要求必须都是连续的,缺点是不能根据下标来直接找到元素,而是要从头开始,根据指针来一次寻找。

顺序表的实现(C语言版)


/**顺序线性表的实现**/

#include<stdio.h>
#include<malloc.h>
#define OVERFLOW_ERROR 0
#define ERROR 1
#define OK 2
/*线性表的初始大小*/
#define LIST_INIT_SIZE 100
/*线性表每次的增量*/
#define LIST_INCREMENT 10

/*定义顺序线性表的结构体*/
typedef struct{
    int *elem;//基址指针
    int length;//当前数组长度
    int listsize;//数组的大小
}Sqlist;


/*初始化线性表*/
int InitList_Sq(Sqlist *L){

    L->elem = (int *)malloc(LIST_INIT_SIZE*sizeof(int));

    if(!L->elem){
        exit(OVERFLOW_ERROR);
    }
    L->length = 0;
    L->listsize = LIST_INIT_SIZE;
    return OK;
}


/*向线性表第position个位置前插入元素*/
int InsertList_Sq(Sqlist *L,int position,int insert_elem){

    //判断插入的位置是否合法
    if(position<1 || position>L->length+1){
        return ERROR;
    }
    //判断当前的数组大小是否超过了已申请到的存储空间
    if(L->length>= L->listsize){
        int *newbase = (int *)realloc(L->elem,(L->listsize + LIST_INCREMENT)*sizeof(int));
        //判断是否重新申请到了空间
        if(!newbase){
            exit(OVERFLOW_ERROR);
        }
        L->elem = newbase;
        L->listsize += LIST_INCREMENT;
    }
    //记录要插入的位置
    int *insert_pointer = &(L->elem[position-1]);
    //将要插入位置后的元素后移
    int *temp= &(L->elem[L->length-1]);
    for(temp;temp>=insert_pointer;temp){
        *(temp+1) = (*temp);
    }
    *insert_pointer = insert_elem;
    ++L->length;
    return OK;
}
/*删除顺序线性表中的第position个元素,并用elem返回其值*/
int ListDelete(Sqlist *L,int position,int *elem){
    //检查position的合法性
    if( (position<1) || (position>L->length) ){
        return ERROR;
    }
    int *delete_pointer = &(L->elem[position-1]);
    elem = delete_pointer;
    int *temp = (L->elem + L->length-1);

    for(++delete_pointer;delete_pointer<=temp;++delete_pointer){
        *(delete_pointer-1) = *delete_pointer;
    }

    --(L->length);
    return OK;

}

/*获取线性表的当前长度*/
int ListLength_Sq(Sqlist L){
    return L.length;
}

/*主函数*/
int main(){
    void ShowList(Sqlist list);
    Sqlist list;
    //初始化数组
    int init_flag = InitList_Sq(&list);
    //向数组中插入元素
    InsertList_Sq(&list,1,23);
    InsertList_Sq(&list,2,34);
    InsertList_Sq(&list,3,56);

    ShowList(list);

    int elem = 0;
    init_flag = ListDelete(&list,2,&elem);//删除第二个元素

    ShowList(list);
    return 0;
}

void ShowList(Sqlist list){

    int i = 0;
    for(i;i<list.length;i++){
        printf("%d\n",list.elem[i]);
    }
    printf("数组长度为\t%d\n",list.length);
}

单链表的实现(C语言版):



/**单链表的实现(头插法)**/

#include<stdio.h>
#include<malloc.h>
#define OVERFLOW_ERROR 0
#define ERROR 1
#define OK 2

/*定义链表的结构体*/
typedef struct LNode{
    int data;//数据
    struct LNode *next;//指向下一个结点
}LNode,*LinkList;

/*初始化一个单链表

    LinkList *L 是一个指向LinkList的指针,存放链表头结点的地址
    int length 是一个整形,用于明确链表的长度

*/
int InitList_L(LinkList *L,int length){
    *L = (LinkList)malloc(sizeof(LNode));

    if((*L) == NULL){
        return ERROR;
    }
    (*L)->next = NULL;

    for(length;length>0;--length){
        LinkList newNode = malloc(sizeof(LNode));
        if(newNode == NULL){
            return ERROR;
        }

        scanf("%d",&(newNode->data));
        newNode->next = (*L)->next;
        (*L)->next = newNode;

    }
    return OK;
}
/*
    插入节点
    LinkList *L 插入的链表
    int position 在position之前插入节点
    int elem 要插入的元素
*/
int InsertList_L(LinkList *L,int position,int elem){

    LinkList p = *L;//记录下链表的初识位置
    int num = 0;
    //找到要插入的位置
    while(p&&num<(position-1)){
        p = p->next;
        num++;
    }
    //如果链表为空,或者是超出了表长
    if(!p || num>position-1){
        return ERROR;
    }
    //申请新的节点
    LinkList temp = (LinkList)malloc(sizeof(LNode));
    temp->data = elem;
    temp->next = p->next;
    p->next = temp;
    return OK;
}
/*
    删除链表中第position个元素,并用elem返回其值
*/
int DeleteList_L(LinkList *L,int position,int *elem){

    LinkList temp = *L;
    int num = 0;
    //将指针指向要删除节点的前一个元素
    while((temp->next)&&(num<position-1)){
        temp = temp->next;
        num++;
    }
    printf("现在指向的元素是%d",temp->data);
    if( (!temp->next) || num>position-1){
        return ERROR;
    }
    LinkList deleteNode = temp->next;
    temp->next = deleteNode->next;
    *elem = deleteNode->data;
    free(deleteNode);
    return OK;
}

/*
    打印链表
*/
int ShowList(LinkList L){

    //打印输出一下链表
    while( L->next != NULL){
    L = L->next;
    printf("%d\n",L->data);
   }

}

/*主函数*/
int main(){

    int length = 0;
    LinkList linkList;
    printf("请输入链表长度\n");
    scanf("%d",&length);
    //初始化链表
    int flag = InitList_L(&linkList,length);

    if(flag == OK){
        printf("初始化成功\n");
    }else{
        printf("初始化失败");
    }
    ShowList(linkList);

    //插入新节点
    flag = ERROR;
    flag = InsertList_L(&linkList,2,34);
    if(flag == OK){
        printf("插入成功\n");
        ShowList(linkList);
    }else{
        printf("插入失败");
    }

    //删除链表
    int deleteNum = 0;
    flag = ERROR;
    flag = DeleteList_L(&linkList,3,&deleteNum);
    if(flag == OK){
        printf("删除成功\n");
        ShowList(linkList);
        printf("被删除元素为%d",deleteNum);
    }else{
        printf("删除失败");
    }
}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值