[数据结构-1] 动态顺序表及其C语言实现

转眼间已经大三下了, 寒假里考虑了很久, 最后还是决定考研, 专业课从大二学的数据结构开始复习,希望能一战上岸吧!

目录

基本概念

算法的时间复杂度

C语言实现


基本概念

顺序表是线性表的一种

线性表: 指数据结构中的数据的结构是线性的, 其他的结构还有树, 图等

顺序表: 线性表的一种, 特点是逻辑上相邻的元素物理内存也是相同的, 与之对应的是链表, 它的物理内存可以是不相邻的

算法的时间复杂度

顺序表通常可以由数组实现, 根据数组的特点, 可知它的算法复杂度(最坏):

  • 取任意索引元素: O(1)
  • 从尾部插入元素: O(1)
  • 从其他位置插入元素: O(n), 因为插入之后后面的元素要移动, 以保证他们还是物理相邻
  • 从尾部删除元素: O(1)
  • 从其他位置删除元素: O(n)

C语言实现

/**
 * @file dynamic_sequence_table.c
 * @author xiaoxiao (you@domain.com)
 * @brief 动态顺序表
 * @version 0.1
 * @date 2022-02-28
 * 
 * @copyright Copyright (c) 2022
 * 
 */
#include <stdio.h>
#include <stdlib.h>

#define InitialLength 10  // 初始长度
#define ElementSize 4     // 链表单个元素的长度
#define ExpansionSize 10 // 每次扩容多少个元素

static unsigned int length = 10; // 当前长度, 初始是10
static unsigned int size = 10; // 初始容量 

// 初始化一个动态链表
int* initalList() {
    int* head = (int*) malloc(InitialLength * ElementSize);
    if (head == NULL) {
        printf("no more momery");
        exit(1);
    }
    for (int i = 0; i < InitialLength; i++) {
        int x;
        // printf("输入初始化顺序表的第%d个数: ", i + 1);
        // scanf("%d", &x);
        head[i] = i;
    }
    return head;
}

// 数组容量扩展,但长度不变
int* expansion(int* head){
    size += ExpansionSize;
    int* new_head = (int*) malloc (ElementSize * length);
    for(int i = 0; i < length; i ++){
        new_head[i] = head[i]; // 原数组复制过来
    }
    free(head);
    printf("扩展数组容量为%d个元素\n", size);
    return new_head;
}

// 尾插法
int* insertInTail(int* head, int data){
    if(length >= size){
        head = expansion(head);
    }
    head[length] = data;
    length ++;
    return head;
}

// 在指定索引插入一个元素
int* insert(int* head, int index, int data){
    if(index < 1 || index > length + 1){
        return head;
    }
    if(length >= size){
        head = expansion(head);
    }
    for(int i = length; i >= index; i--){
        head[i] = head[i - 1];
    }
    head[index - 1] = data;
    length ++;
    return head;
}

// index永远从1开始
int* delete(int* head, int index){
    if(index > length){
        printf("删除的索引超过顺序表长度\n");
    }
    else {
        for(int i = index; i < length; i ++){
            head[i - 1] = head[i];
        }
        length --;
    }
    return head;
}

// 打印数组
void printList(int* head) {
    printf("共%d个元素: ", length);
    for(int i = 0; i < length; i++){
        printf("%d ", head[i]);
    }
    printf("\n");
}

int getByIndex(int* head, int index){
    if(index > length){
        printf("取值的索引超过顺序表长度\n");
        return -1;
    }
    else{
        return head[index - 1];
    }
}

// 主函数
int main() {
    printf("----------------------\n");
    int* head = NULL;  // head[0]初始为NULL
    head = initalList();
    head = insertInTail(head, 3);
    printList(head);
    printf("%d", getByIndex(head, 5));
    printf("\n----------------------\n");
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值