SDKD 软件18 链表(1)#函数题,编程题#

6-1 带头结点的单链表就地逆置 (10 分)

思路

首先有两种特殊情况,空链表无法逆置,只有一个元素无需逆置
其他情况可统一为以下代码中的方法
将数据元素倒序连接,不断向前移动头结点

代码

void ListReverse_L(LinkList &L)
{
    /*
        cur:当前
        nex:下一个
    */
    LNode *nex, *cur = L->next;
    if(cur && cur->next) //判断是否有第一个节点以及第二个节点
    {
        nex = L->next->next;//将头节点的后第二个节点取下
        L->next->next = NULL;
        while(nex)
        {
            cur = L->next;
            L->next = nex;
            nex = nex->next;
            L->next->next = cur;
        }
    }
}

7-1 两个有序链表序列的合并 (20 分)

思路

不断从两个链表的头部取取节点,哪个链表的头结点的data小就将其链接到结果链表的末端

代码

//库函数头文件包含
#include <stdio.h>
#include <malloc.h>
#include <stdlib.h>

//函数状态码定义
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
#define OVERFLOW -2

typedef int Status;
typedef int ElemType; //假设线性表中的元素均为整型

typedef struct LNode
{
    ElemType data;
    struct LNode *next;
} LNode, *LinkList;

Status ListCreate_L(LinkList &L)
{
    LNode *rearPtr, *curPtr; //一个尾指针,一个指向新节点的指针
    L = (LNode *)malloc(sizeof(LNode));
    if (!L)
        exit(OVERFLOW);
    L->next = NULL; //先建立一个带头结点的单链表
    rearPtr = L;    //初始时头结点为尾节点,rearPtr指向尾巴节点
    while (1)       //每次循环都开辟一个新节点,并把新节点拼到尾节点后
    {
        curPtr = (LNode *)malloc(sizeof(LNode)); //生成新结点
        if (!curPtr)
            exit(OVERFLOW);
        scanf("%d", &curPtr->data); //输入元素值
        if (curPtr->data == -1)
            break;
        curPtr->next = NULL; //最后一个节点的next赋空
        rearPtr->next = curPtr;
        rearPtr = curPtr;
    }
    return OK;
}

void ListPrint_L(LinkList &L)
{
    if (L->next)
    {
        //输出单链表
        LNode *p = L->next; //p指向第一个元素结点
        while (p != NULL)
        {
            if (p->next != NULL)
                printf("%d ", p->data);
            else
                printf("%d", p->data);
            p = p->next;
        }
    }
    else
    {
        printf("NULL");
    }
}

void ListMerge_L(LinkList a, LinkList b, LinkList c)
{
    a = a->next;
    b = b->next;
    while (a && b)
    {
        if (a->data <= b->data)
        {
            c->next = a;
            a = a->next;
        }
        else
        {
            c->next = b;
            b = b->next;
        }
        c = c->next;
    }
    c->next = a ? a : b;
}

int main()
{
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    freopen("out.txt", "w", stdout);
#endif
    LinkList L1, L2, L;
    if ((ListCreate_L(L1) && ListCreate_L(L2)) != OK)
    {
        printf("表创建失败!!!\n");
        return -1;
    }
    L = (LNode *)malloc(sizeof(LNode));
    if (!L)
    {
        printf("表创建失败!!!\n");
        return -1;
    }
    ListMerge_L(L1, L2, L);
    ListPrint_L(L);
    return 0;
}

STL代码

#include <bits/stdc++.h>
using namespace std;
vector<int> vec;
int main()
{
    for (int i = 0; i < 2; ++i)
    {
        int a;
        while (1)
        {
            cin >> a;
            if (a == -1)
                break;
            vec.push_back(a);
        }
    }
    sort(vec.begin(), vec.end());
    if (vec.begin() == vec.end())
        printf("NULL");
    else
        for (vector<int>::iterator it = vec.begin(); it != vec.end(); it++)
        {
            if (it != vec.begin())
                cout << " ";
            cout << *it;
        }
}

7-2 两个有序链表序列的交集 (20 分)

思路

由于该题目所提供的链表是非降序的,那么我们就很容易求出链表的的并集
我们采取这样一种方法:
从两个链表的前端开始比较元素的大小,谁的元素更小就丢弃该节点,直到某个链表中没有元素了结束操作.
中途发生两节点相同的情况就copy此节点放在答案链表的尾部.

代码

//库函数头文件包含
#include <stdio.h>
#include <malloc.h>
#include <stdlib.h>

//函数状态码定义
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define INFEASIBLE -1
#define OVERFLOW -2

typedef int Status;
typedef int ElemType; //假设线性表中的元素均为整型

typedef struct LNode
{
    ElemType data;
    struct LNode *next;
} LNode, *LinkList;

Status ListCreate_L(LinkList &L)
{
    LNode *rearPtr, *curPtr; //一个尾指针,一个指向新节点的指针
    L = (LNode *)malloc(sizeof(LNode));
    if (!L)
        exit(OVERFLOW);
    L->next = NULL; //先建立一个带头结点的单链表
    rearPtr = L;    //初始时头结点为尾节点,rearPtr指向尾巴节点
    while (1)       //每次循环都开辟一个新节点,并把新节点拼到尾节点后
    {
        curPtr = (LNode *)malloc(sizeof(LNode)); //生成新结点
        if (!curPtr)
            exit(OVERFLOW);
        scanf("%d", &curPtr->data); //输入元素值
        if (curPtr->data == -1)
            break;
        curPtr->next = NULL; //最后一个节点的next赋空
        rearPtr->next = curPtr;
        rearPtr = curPtr;
    }
    return OK;
}

void ListPrint_L(LinkList &L)
{
    if (L->next)
    {
        //输出单链表
        LNode *p = L->next; //p指向第一个元素结点
        while (p != NULL)
        {
            if (p->next != NULL)
                printf("%d ", p->data);
            else
                printf("%d", p->data);
            p = p->next;
        }
    }
    else
        printf("NULL");
}

Status ListMerge_L(LinkList a, LinkList b, LinkList c)
{
    a = a->next;
    b = b->next;
    while (a && b)
    {
        if (a->data <= b->data)
        {
            c->next = a;
            a = a->next;
        }
        else
        {
            c->next = b;
            b = b->next;
        }
        c = c->next;
    }
    c->next = a ? a : b;
    return OK;
}

Status ListIntersection_L(LinkList a, LinkList b, LinkList cur)
{
    LinkList tmp;
    a = a->next;
    b = b->next; 
    while (a && b)
    {
        if (a->data < b->data)
            a = a->next;
        else if (a->data > b->data)
            b = b->next;
        else
        {
            tmp = (LNode *)malloc(sizeof(LNode));
            if (!tmp)
                exit(OVERFLOW);
            tmp->data = a->data;
            tmp->next = NULL;
            cur->next = tmp;
            cur = tmp;
            a = a->next;
            b = b->next;
        }
    }
    //cur->next = NULL;
    return OK;
}

int main()
{
#ifndef ONLINE_JUDGE
    freopen("in.txt", "r", stdin);
    freopen("out.txt", "w", stdout);
#endif
    LinkList L1, L2, L;
    if ((ListCreate_L(L1) && ListCreate_L(L2)) != OK)
    {
        printf("表创建失败!!!\n");
        return -1;
    }
    L = (LNode *)malloc(sizeof(LNode));
    if (!L)
    {
        printf("表创建失败!!!\n");
        return -1;
    }
    ListIntersection_L(L1, L2, L);
    ListPrint_L(L);
    return 0;
}

STL代码

#include <bits/stdc++.h>
using namespace std;
vector<int> v, vec[2];

int main()
{
    for (int i = 0; i < 2; ++i)
    {
        int a;
        while (1)
        {
            cin >> a;
            if (a == -1)
                break;
            vec[i].push_back(a);
        }
    }

    set_intersection(vec[0].begin(), vec[0].end(), vec[1].begin(), vec[1].end(), inserter(v, v.begin()));
    if (v.begin() == v.end())
        printf("NULL");
    else
        for (vector<int>::iterator it = v.begin(); it != v.end(); it++)
        {
            if (it != v.begin())
                cout << " ";
            cout << *it;
        }
}
posted @ 2019-09-06 10:14  YuKi_hahaha  阅读(240)  评论(0编辑  收藏  举报