首页 > 编程语言 >静态链表(C++)

静态链表(C++)

时间:2024-07-25 10:32:43浏览次数:13  
标签:index head curser 静态 StaticList C++ 链表 pool size

一,静态链表

简介

静态链表使用连续的内存,每个结点记录一个数据和指向下一结点的指针。
可以高效的进行插入删除操作。
是用整形游标代替结点指针的“单链表”。

结构

  1. 结点类型
struct node{
    size_t curser;
    int value;
};
  1. 静态链表类型
    链表中储存结点构成的数组
struct StaticList {
    node* head;
    node* pool;
    size_t size;

    StaticList();
    StaticList(size_t size);
    void insert(size_t index, int value);
    void del(size_t index);
    size_t len() const;
    size_t get(size_t index) const;
    void append(int value);
    void print_a() const;
    void print_v() const;
    size_t _malloc_list();
};

二,操作

初始化

预留链表头部的两个结点分别命名为head和pool,head和pool分别是两个独立的链表的头节点。
head是已记录数据的结点组成的链表的头节点,而pool用来记录没有数据的。

初始时没有储存数据,head的游标(curser)指向head本身。pool的游标指向下一个空结点(2),以此类推,最后一个空结点指向pool(1)。

构造函数如下:

StaticList::StaticList(){
    StaticList(20);
    size = 20;
}

StaticList::StaticList(size_t size){
    head = (node*)malloc(sizeof(node)*(size+2));
    pool = head+1;
    head->curser = 0;
    head->value = 0;
    for(size_t i=1; i <= size+1; i++){
        head[i].curser = i+1;
        head[i].value = 0;
    }
    head[size+1].curser = 1;
    this->size = size;
}

尾部添加元素

找到head的链表中游标指向的0的结点即最后一个记录数据的结点,操作与单链表相似。
需要先从pool中申请一个空结点:

size_t StaticList::_malloc_list(){
    if (pool->curser == 1){
        throw 1;
    }
    size_t n = pool->curser;
    pool->curser = head[pool->curser].curser;
    return n;
}

再把数据添加到空结点中:

void StaticList::append(int value){ 
    size_t i=0;
    size_t newnode = _malloc_list();
    for(; head[i].curser != 0; i=head[i].curser);
    head[newnode].value = value;
    head[newnode].curser = head[i].curser;
    head[i].curser = newnode;
}

获取链表储存数据数

size_t StaticList::len() const {
    size_t length=0;
    for(size_t i=head->curser; i!=0; i=head[i].curser){
        length++;
    }
    return length;
}

插入元素

插入同样用_malloc_list申请空结点,在修改head链表的指针,进行插入。

void StaticList::insert(size_t index, int value){
    size_t target = 0;
    if(len()<=index){
        throw 1;
    }
    for(; index > 0; index--){
        target = head[target].curser;
    }
    size_t newnode = _malloc_list();
    head[newnode].curser = head[target].curser;
    head[newnode].value = value;
    head[target].curser = newnode;
}

删除元素

直接修改pool链表的指针,跳过待删除的结点即可。
void StaticList::del(size_t index){
    size_t target1 = 0, target2=0;
    if (len()-1 < index){
        throw 1;
    }
    for(; index>0; index--)
        target1 = head[target1].curser;
    target2 = head[target1].curser;
    head[target1].curser = head[target2].curser;
    head[target2].curser = pool->curser;
    pool->curser = target2;
}

获取元素

size_t StaticList::get(size_t index) const {
    size_t target = 0;
    if (len()-1 < index)
        throw 1;
    for(;index!=0; index--){
        target = head[target].curser;
    }
    return target;
}

打印链表

//打印详细信息
void StaticList::print_a() const {
    cout << "index  curser  value" << endl;
    for(size_t i=0; i<=size+1; i++){
        cout << i << '\t' << head[i].curser << '\t' << head[i].value << endl;
    }
}

// 打印值
void StaticList::print_v() const {
    size_t i=head->curser;
    for(; head[i].curser!=0; i=head[i].curser){
        cout << head[i].value << ' ';
    }
    cout << head[i].value << endl;
}

三,完整代码

点击查看代码
#include <iostream>
#include <vector>

using std::vector;
using std::cout, std::cin, std::endl;

struct node{
    size_t curser;
    int value;
};

struct StaticList {
    StaticList();
    StaticList(size_t size);

    void insert(size_t index, int value);
    void del(size_t index);
    size_t len() const;
    size_t get(size_t index) const;
    void append(int value);
    void print_a() const;
    void print_v() const;
    size_t _malloc_list();
    node* head;
    node* pool;
    size_t size;
};

StaticList::StaticList(){
    StaticList(20);
    size = 20;
}

StaticList::StaticList(size_t size){
    head = (node*)malloc(sizeof(node)*(size+2));
    pool = head+1;
    head->curser = 0;
    head->value = 0;
    for(size_t i=1; i <= size+1; i++){
        head[i].curser = i+1;
        head[i].value = 0;
    }
    head[size+1].curser = 1;
    this->size = size;
}

void StaticList::print_a() const {
    cout << "index  curser  value" << endl;
    for(size_t i=0; i<=size+1; i++){
        cout << i << '\t' << head[i].curser << '\t' << head[i].value << endl;
    }
}

void StaticList::print_v() const {
    size_t i=head->curser;
    for(; head[i].curser!=0; i=head[i].curser){
        cout << head[i].value << ' ';
    }
    cout << head[i].value << endl;
}

void StaticList::append(int value){ 
    size_t i=0;
    size_t newnode = _malloc_list();
    for(; head[i].curser != 0; i=head[i].curser);
    head[newnode].value = value;
    head[newnode].curser = head[i].curser;
    head[i].curser = newnode;
}

size_t StaticList::_malloc_list(){
    if (pool->curser == 1){
        throw 1;
    }
    size_t n = pool->curser;
    pool->curser = head[pool->curser].curser;
    return n;
}

size_t StaticList::len() const {
    size_t length=0;
    for(size_t i=head->curser; i!=0; i=head[i].curser){
        length++;
    }
    return length;
}

void StaticList::del(size_t index){
    size_t target1 = 0, target2=0;
    if (len()-1 < index){
        throw 1;
    }
    for(; index>0; index--)
        target1 = head[target1].curser;
    target2 = head[target1].curser;
    head[target1].curser = head[target2].curser;
    head[target2].curser = pool->curser;
    pool->curser = target2;
}

size_t StaticList::get(size_t index) const {
    size_t target = 0;
    if (len()-1 < index)
        throw 1;
    for(;index!=0; index--){
        target = head[target].curser;
    }
    return target;
}

void StaticList::insert(size_t index, int value){
    size_t target = 0;
    if(len()<=index){
        throw 1;
    }
    for(; index > 0; index--){
        target = head[target].curser;
    }
    size_t newnode = _malloc_list();
    head[newnode].curser = head[target].curser;
    head[newnode].value = value;
    head[target].curser = newnode;
}

int main(){
    StaticList list(10);
    list.append(2);
    list.append(3);
    list.append(3);
    list.append(3);
    list.insert(4, 1);
    list.del(3);
    list.print_a();
    list.print_v();
    return 0;
}

标签:index,head,curser,静态,StaticList,C++,链表,pool,size
From: https://www.cnblogs.com/lianzhy/p/18322371

相关文章

  • ONNXRuntime_C++安装教程
    1打开VisualStudio2017,新建空项目helloworld 2浏览输入onnxruntime,安装第一个,版本选择1.18.1 3配置PATH环境变量4配置项目包含目录 5配置库目录6配置链接器 配置opencVhttps://blog.csdn.net/qq_27825451/article/details/103036687 无法启动应用......
  • Java————链表
    目录前言:1.链表的概念2.链表的结构2.1带头的和不带头的2.2单向和双向2.3循环和非循环3.链表的实现3.1双向不带头不循环链表:3.2单向不带头不循环链表:4.LinkedList的使用4.1什么是LinkedList4.2LinkedList的使用5.LinkedList的遍历5.1foreach遍历5.2使用迭代器遍......
  • C++自学笔记15(数组)
    指针是C++中数组的工作方式,没有指针基础可以看笔记6。数组就是一堆变量的集合,有没有感觉与结构体很相似?让我们来考虑下在结构体中我们仅仅是定义了几个变量例如定义x,y坐标与speed速度。如果我们需要64个变量表示某个东西的64种状态,那么你会看到inta0=0;inta1=1;inta2......
  • C++自学笔记16(字符串与字符串字面量)
    当我们想在电脑上以文本方式表示东西时,一个单词、一个句子、一大段文章都叫做字符串。字符串就是为了我们去处理文字文本的方法。字符串实际上就是字符组成的数组或指针(数组就是指针的一种)。(有人会问数组不是储存数字么?怎么储存字符?因为ASCLL码表将所有字母、数字、符号翻译......
  • C++11——lambda表达式
    一、前言在C++98中,如果想要对一个数据集合中的元素进行排序,可以使用std::sort方法。intmain(){ intarray[]={4,1,8,5,3,7,0,9,2,6}; //默认按照小于比较,排出来结果是升序 sort(array,array+sizeof(array)/sizeof(array[0])); //如果需要降序,需要改变元素......
  • C++学习笔记(03)——通讯录管理系统设计
    记录一下利用C++来实现一个通讯录管理系统系统中需要实现的功能如下:添加联系人:向通讯录中添加新人,信息包括(姓名、性别、年龄、联系电话、家庭住址)最多记录1000人显示联系人:显示通讯录中所有联系人信息删除联系人:按照姓名进行删除指定联系人查找联系人:按照姓名查看指定联系人......
  • 卡皮巴拉(c++)
    题目描述有一种卡皮巴拉玩偶,它有头、身体、四肢三个部分,每个部分需要使用不同的材料制作。玩具公司生产了很多批次的卡皮巴拉玩偶,每个批次的玩偶的三个部分都分别有多种款式(每种款式只需使用一种材料)。现在有`k`批次的卡皮巴拉玩偶,每个批次的玩偶的头、身体和四肢的款式分别......
  • 成员函数(c++)
    题目描述针对上一题的情形,除了在结构体外新设计一个函数 get_grade 外,我们可以用另外一种方法,给类添加一个成员函数,如下所示。structStudent{intx;inty;intz;intget_grade(){//todo}};此后,对于每一个 Student 类的对象 s,我们可以......
  • 图的最短路径算法(SPFA,Dijkstra,Bellman_Ford)(迪杰斯特拉算法,Spfa算法,贝尔曼-福特算
    目录Dijkstra迪杰斯特拉算法写法时间复杂度例题描述输入描述输出描述样例输入用例输出用例写法Spfa算法例题描述输入描述输出描述样例输入用例输出用例写法Bellman_Ford算法(贝尔曼-福特算法)写法例题描述输入描述输出描述样例输入样例输出样例......
  • 【知识扩展】C/C++编译原理
    C/C++编译原理一、前言二、编译原理1、预处理2、编译3、汇编4、链接三、头文件和库文件1、头文件2、库文件四、编译器1、GCC编译器1.1、编译过程1.1.1、预处理1.1.2、编译1.1.3、汇编1.1.4、链接1.2、创建静态库1.2.1、静态库源码编译成.o的文件1.2.2、编译静态库1.......