409数据结构学习强化——常见数据结构定义和算法总结(二)

简介: 409数据结构学习强化——常见数据结构定义和算法总结

2.3.5.删除链表中的重复元素

897f91ea488e437280ebd1fddfc4c064.png

void Delete(LinkList &L) {
    LNode *p = L->next;
    while (p) {
        LNode *post = p->next;    //post指向p的下一个结点
        while (post && post->data == p->data) {    //post存在并且值和p相等时
            LNode *temp = post;    //temp指向post
            post = post->next;    //post向后移动
            p->next = post;    //将p的下一个结点修改为post
            free(temp);
        }
        p = p->next;
    }
}

2.3.6.将两个递增链表合并成一个递减链表31bcee4271af4b03b808c33a52267356.png

void Merge(LinkList &L1, LinkList L2) {
    LNode *p = L1->next, *q = L2->next, *temp;
    L1->next = NULL;    //L1断链
    while (p && q) {
        if (p->data <= q->data) {    //当前p指向的元素更小
            temp = p->next;    //temp指向p的下一个结点
            p->next = L1->next;    //将p用头插法插入L1
            L1->next = p;
            p = temp;    //p指向temp
        } else {    //当前q指向的元素更小
            temp = q->next;
            q->next = L1->next;
            L1->next = q;
            q = temp;
        }
    }//while
    while (p) {    //将剩余节点插入L1
        temp = p->next;
        p->next = L1->next;
        L1->next = p;
        p = temp;
    }
    while (q) {
        temp = q->next;
        q->next = L1->next;
        L1->next = q;
        q = temp;
    }
    return;
}

2.3.7.将两个递增链表合并为一个递增链表

LNode *Merge(LinkList L1, LinkList L2) {
    LNode *p = L1->next, *q = L2->next, *r, *temp;
    LNode *L = (LNode*)malloc(sizeof(LNode));
    L->next = NULL;
    r = L;
    while (p && q) {
        if (p->data <= q->data) {    //当前p指向的结点小于等于q
            temp = p->next;
            r->next = p;    //p尾插法插入L中
            r = p;
            p = temp;
        } else {
            temp = q->next;
            r->next = q;
            r = q;
            q = temp;
        }
    }
    while (p) {    //插入剩余结点
        temp = p->next;
        r->next = p;
        r = p;
        p = temp;
    }
    while (q) {
        temp = q->next;
        r->next = q;
        r = q;
        q = temp;
    }
    r->next = NULL;    //将r的next指针置空
    return L;
}

2.3.8.判断链表是否对称68d0f4f27e6d4417a2c3776c06645b4f.png

bool ans(LinkList L) {
  LNode* post = L->prior, * pre = L->next;    //前后指针
    //表中元素为奇数时,终止条件为两者移动到同一结点
    //表中元素为偶数时,终止条件为两者后指针的next指向前指针
  while (post != pre && post->next != pre) {    
    if (post->data != pre->data) return false;    //前后指针的指针域不相等
    pre = pre->next;    //前指针前移
    post = post->prior;    //后指针后移
  }
    //表对称
  return true;
}
bool ans(LinkList L) {
  LNode* p = L->next;
  int len = 0;    //记录表中的元素个数
  while (p != L) {
    p = p->next;
    len++;
  }
  int a = (int*)malloc(len * sizeof(int));    //定义跟链表结点个数相等的长度的数组
  len = 0;
  p = L->next
  while (p != L) {    //遍历链表,用数组保存链表中每个结点的值
    a[len] = p->next;
    p = p->next;
  }
    //遍历数组,前后指针指向元素的值不相等,返回false
  for (int i = 0, j = len - 1; i < j; i++, j--) {
    if (a[i] != a[j]) return false;
  }
  return true;
}

2.3.9.依次输出链表中结点值最小的元素

da5a120bd343499eb0f1dd383d35b0a1.png

void DeleteMin(LinkList &L) {
    LNode *p = L->next, *ppre = L->next, *min, *minpre;
    while (L->next != L) {
        p = L->next;
        ppre = L;
        int tempMin = INT_MAX;    //当前最小值
        while (p != L) {
            if (p->data < tempMin) {    //当前结点值更小,更新最小结点
                min = p;
                minpre = ppre;
            }    //p向后移动
            ppre = p;
            p = p->next;
        }
        cout << min->data;    //输出最小结点的值
        minpre->next = min->next;    //删除min结点
        free(min);
    }//while
    free(L);    //删除头结点
}

2.3.10.真题a822bd0933d74051bf109284bedcdd31.png

void ans(LinkList L, int k){
    LNode *p = L->link, *q = L->link;
    for (int i = 0; i < k; i++) p = p->link;    //p指针向后移动k个结点
    while (p) {
        p = p->link;
        q = q->link;
    }
    cout << q->data;
}

0d293bb78b334ecf8ee9dfdc7392f538.png

void ans(LinkList str1, LinkList str2) {
  LNode *p = str1->next, *q = str2->next;
  int len1 = 0, len2 = 0;
  while (p) {    //遍历str1,得到str1的长度
    len1++;
    p = p->next;
  }
  while (q) {    //遍历str2,得到str2的长度
    len2++;
    q = q->next;
  }
  int len = abs(len1 - len2);    //得到两表长度之差
  p = str1->next;    //重置pq指向第一个结点
  q = str2->next;
  if (len1 >= len2) {    //长表向前移动,使得两表剩余元素相等
    for (int i = 0; i < len; i++) p = p->next;
  }
  else {
    for (int i = 0; i < len; i++) q = q->next;
  }
  while (p) {    //遍历剩余结点,找到两者指向的第一个共同结点
    if (p == q) return p;
    p = p->next;
    q = q->next;
  }
  return NULL;    //两者没有共同后缀
}

c0f0efeb281542c5863afd80a37ddea1.png

void ans(LinkList &L){
    bool A[n + 1];    //长度为n + 1的数组,用来标记该数是否出现过
    for (int i = 0; i < n + 1; i++) A[i] = false;    //初始化A数组
    LNode *p = head->next, *pre = head;
    while (p) {
        int t = abs(p->data);    //取当前结点值的绝对值
        if (A[t]) {    //该值出现过,删除该结点
            LNode *r = p->next;
            pre->next = r;
            free(p);
            p = r;
        } else {    //该值没有出现过,在数组A中标记该值,p和pre向后移动
            A[t] = true;
            pre = p;
            p = p->next;
        }
    }//while
}

6e9952902c0a498ab760546c23af4047.png

void ans(NODE *L) {
  NODE* p = L->next, *f = L->next, *s = L->next, *q, *t;
  while (f->next->next && f->next) {  //找到前半链的最后一个结点
    f = f->next->next;    //快指针移动两个结点
    s = s->next;    //慢指针移动一个结点
  }
  q = s->next;  //q指向后半链的第一个结点
  s->next = NULL; //前半链后半链断开
  LNode* post = (NODE*)malloc(sizeof(NODE));
  post->next = NULL;
  while (q) { //后半链逆置
    t = q->next;
    q->next = post->next;
    post->next = q;
    q = t;
  }
  q = post->next; //q指向逆置后的后半链的第一个结点
  while (q) {
    r = q->next;  //r指向后半链的下一个结点
    t = p->next;  //t指向前半链下一个插入位置
    q->next = p->next;
    p->next = q;
    q = r;  //重置pq
    p = t;
  }
}

3.栈

3.1.栈的数据结构定义

3.1.1.顺序栈

#define MAXSIZE 100
typedef struct Stack {
    int data[MAXSIZE];
    int top = -1;
}Stack;

3.1.2.链栈

typedef struct LStack {
    int data;
    struct LStack *next;
}SNode, *LStack;

3.2.顺序栈的操作

3.2.1.栈的初始化

void InitStack (Stack &S) {
    S.top = -1;
}

3.2.1.入栈

bool Push(Stack &S, int key) {
    if (S.top == MAXSIZE - 1) return false;    //栈满
    S.data[++top] = key;
    return true;
}

3.2.2.出栈

bool Pop (Stack &S, int &key) {
    if (S.top == -1) return false;    //栈空
    key = S.data[top--];
    return true;
}

3.2.3.判断栈空

bool IsEmpty (Stack S) {
    if (S.top == -1) return true;
    else return false;
}

3.3.链栈的基本操作

3.3.1.初始化

void InitStack (LStack &S) {
    SNode *s = (SNode*)malloc(Sizeof(SNode));
    S->next = NULL;
}

3.3.2.入栈

void Push (LStack &S, int key) {
    SNode *p = (SNode*)malloc(sizeof(SNode));
    p->data = key;
    p->next = S->next;    //头插法
    S->next = p;
}

3.3.3.出栈

bool Pop (LStack &S, int &key) {
    if (S->next == NULL) return false;    //栈空
    SNode *p = S->next;
    key = p->data;    //key保存栈顶元素的值
    S->next = p->next;
    free(p);
}

3.3.4.判断栈空

bool IsEmpty(LStack &S) {
    if (S->next == NULL) return true;
    else return false;
}


相关文章
|
12天前
|
机器学习/深度学习 算法 存储
[数据结构]——算法的时间复杂度和空间复杂度
[数据结构]——算法的时间复杂度和空间复杂度
|
5天前
|
算法
重拾数据结构和算法——脑图
重拾数据结构和算法——脑图
11 0
|
10天前
|
算法 搜索推荐 Java
Java数据结构 -- 常见算法分析(查找算法、排序算法)精解详解!!!
Java数据结构 -- 常见算法分析(查找算法、排序算法)精解详解!!!
7 0
|
11天前
|
存储 搜索推荐 算法
C语言数据结构算法,常用10种排序实战
插入排序(Insertion Sort) 希尔排序(Shell Sort) 选择排序(Selection Sort) 冒泡排序(Bubble Sort) 归并排序(Merge Sort) 快速排序(Quick Sort) 堆排序(Heap Sort) 基数排序(Radix Sort)
11 1
C语言数据结构算法,常用10种排序实战
|
14天前
|
存储
数据结构-树的介绍、树的定义和基本术语
树是一种非线性的数据结构,是以分支关系定义的层次结构,比如人类社会中的族谱、及各种机制、组织的关系都可以用树形象的表示。重点学习二叉树的存储和相关操作,还要讨论树、森林、二叉树的转换关系。
20 0
|
17天前
|
缓存 算法 Java
数据结构~缓存淘汰算法--LRU算法(Java的俩种实现方式,万字解析
数据结构~缓存淘汰算法--LRU算法(Java的俩种实现方式,万字解析
|
19天前
|
算法 数据安全/隐私保护 计算机视觉
基于二维CS-SCHT变换和LABS方法的水印嵌入和提取算法matlab仿真
该内容包括一个算法的运行展示和详细步骤,使用了MATLAB2022a。算法涉及水印嵌入和提取,利用LAB色彩空间可能用于隐藏水印。水印通过二维CS-SCHT变换、低频系数处理和特定解码策略来提取。代码段展示了水印置乱、图像处理(如噪声、旋转、剪切等攻击)以及水印的逆置乱和提取过程。最后,计算并保存了比特率,用于评估水印的稳健性。
|
3天前
|
机器学习/深度学习 算法 数据安全/隐私保护
基于DCT变换和位平面分解的数字水印嵌入提取算法matlab仿真
这是一个关于数字水印算法的摘要:使用MATLAB2022a实现,结合DCT和位平面分解技术。算法先通过DCT变换将图像转至频域,随后利用位平面分解嵌入水印,确保在图像处理后仍能提取。核心程序包括水印嵌入和提取,以及性能分析部分,通过PSNR和NC指标评估水印在不同噪声条件下的鲁棒性。
|
4天前
|
算法 数据安全/隐私保护 C++
基于二维CS-SCHT变换和扩频方法的彩色图像水印嵌入和提取算法matlab仿真
该内容是关于一个图像水印算法的描述。在MATLAB2022a中运行,算法包括水印的嵌入和提取。首先,RGB图像转换为YUV格式,然后水印通过特定规则嵌入到Y分量中,并经过Arnold置乱增强安全性。水印提取时,经过逆过程恢复,使用了二维CS-SCHT变换和噪声对比度(NC)计算来评估水印的鲁棒性。代码中展示了从RGB到YUV的转换、水印嵌入、JPEG压缩攻击模拟以及水印提取的步骤。
|
5天前
|
机器学习/深度学习 算法 数据可视化
基于BP神经网络的32QAM解调算法matlab性能仿真
```markdown - 32QAM解调算法运用BP神经网络在matlab2022a中实现,适应复杂通信环境。 - 网络结构含输入、隐藏和输出层,利用梯度下降法优化,以交叉熵损失最小化为目标训练。 - 训练后,解调通过前向传播完成,提高在噪声和干扰中的数据恢复能力。 ``` 请注意,由于字符限制,部分详细信息(如具体图示和详细步骤)未能在摘要中包含。