2020-11-01

有序链表操作

掌握有序链表的基本操作:插入、删除、查找。

掌握链表遍历器的使用方法。

#pragma once
#include <iostream>


using namespace std;

class OutOfBounds {
public:
    OutOfBounds() {
        cout << "Wrong" << endl;
    }
};
class Title {
public:
    Title() {
        cout << "Title error" << endl;
    }
};
int newProgram(size_t size) {
    throw Title();
}
template <class T>
class fjxChainNode {
public:
    T data;
    fjxChainNode<T>* node;
};
template <class T>
class myChain {
public:
    myChain() { head = 0; }//构造函数
    ~myChain();//析构函数,就是删掉链表中的每一个节点
    bool IsEmpty()const {//判断链表是不是没有元素
        return head == 0;
    }
    int myLength()const;//返回链表的长度
    void fjxErase();//删除链表中的所有节点
    void fjxOutput(ostream& out) const;//输出链表
    int fjxSearch(const T& x)const;//寻找是否存在x这个值
    myChain<T>& fjxInsert(int k, const T& x);//插入节点
    myChain<T>& fjxAutoNew(const T& x);//自动寻找位置并插入节点
    myChain<T>& fjxAppend(const T& x);//在链表的最后加上元素
    myChain<T>& fjxMerge(myChain<T>& A, myChain<T>& B);//求两个链表的和
    fjxChainNode<T>* last;
    fjxChainNode<T>* head;
};
//析构函数
template <class T>
myChain<T>::~myChain<T>() {
    fjxErase();
}
//返回链表的长度
template <class T>
int myChain<T>::myLength()const {
    fjxChainNode<T>* p = head;
    int length = 0;
    while (p != NULL) {
        length++;
        p = p->node;//每往下移动一个节点,len就加1;
    }
    return length;
}
//第几个元素是x元素
template <class T>
int myChain<T>::fjxSearch(const T& x)const {
    fjxChainNode<T>* p = head;
    int index = 1;
    while (p != NULL && p->data != x) {//如果存在p节点,并且没有当前元素的值不为x,就往下移动,寻找下一个节点
        p = p->node;
        index++;
    }
    if (p != NULL) {//如果当前节点存在的话,返回index,表示元素在第index个,如果index为0,说明没有找到
        return index;
    }
    return 0;
}
//输出链表
template<class T>
void myChain<T>::fjxOutput(ostream& out)const {
    fjxChainNode<T>* p;
    for (p = head; p != NULL; p = p->node) {
        out << p->data;
        if (!p->node) {
            out << endl;
        }
        else {
            out << ",";
        }
    }
}
//重载操作符
template<class T>
std::ostream& operator<<(std::ostream& out, const myChain<T>& x) {
    x.fjxOutput(out);
    return out;
}
//插入操作
template <class T>
myChain<T>& myChain<T>::fjxInsert(int k, const T& x) {
    if (k < 0)throw OutOfBounds();
    fjxChainNode<T>* p = head;
    for (int index = 1; index < k && p != NULL; index++) {
        p = p->node;//移动到第k个节点
    }
    if (k > 0 && p == NULL) {
        throw OutOfBounds();
    }
    fjxChainNode<T>* t = new fjxChainNode<T>();
    t->data = x;
    if (k) {
        t->node = p->node;
        p->node = t;
    }
    else {
        t->node = head;
        head = t;
    }
    return *this;
}
//自动插入操作
template <class T>
myChain<T>& myChain<T>::fjxAutoNew(const T& x) {
    fjxChainNode<T>* p = head;
    //创建新增节点 
    fjxChainNode<T>* t = new fjxChainNode<T>();
    t->data = x;
    //空链表时 
    if (p == 0) {
        head = t;
        return *this;
    }
    else {
        if (x <= head->data) {
            t->node = p;
            head = t;
            return *this;
        }
        //中间 
        while (p->node) {
            if (p->data <= x && x <= p->node->data) {
                t->node = p->node;
                p->node = t;
                break;
            }
            p = p->node;
        }
        //尾部 
        p->node = t;
    }
    return *this;
}
template <class T>
void myChain<T>::fjxErase() {
    fjxChainNode<T>* next;
    while (head) {
        next = head->node;
        delete head;
        head = next;
    }
}
template <class T>
myChain<T>& myChain<T>::fjxAppend(const T& x) {
    fjxChainNode<T>* t = new fjxChainNode<T>();
    t->data = x;
    t->node = 0;//空指针还有野指针必须附上零或者空
    if (head) {
        last->node = t;//代表使last的下一个节点是t
        last = t;
    }
    else {
        head = last = t;
    }
    return *this;
}
template <class T>
myChain<T>& myChain<T>::fjxMerge(myChain<T>& A, myChain<T>& B)
{
    fjxChainNode<T>* pa = A.head;
    fjxChainNode<T>* pb = B.head;
    fjxChainNode<T>* pc = 0;
    fjxChainNode<T>* head = 0;
    fjxChainNode<T>* q = 0;
    while (pa != NULL && pb != NULL) {
        if (pa->data <= pb->data) {
            q = pa;
            pa = pa->node;
        }
        else {
            q = pb;
            pb = pb->node;
        }
        if (pc == 0) { head = q; pc = q; }
        else { pc->node = q; pc = q; }
    }
    if (pa != NULL) pc->node = pa;
    else pc->node = pb;
    A.head = 0;
    B.head = 0;
    return *this;
}
//遍历器
template <class T>
class ChainIterator {
public:
    T* Initialize(const myChain<T>& c) {
        location = c.head;
        if (location) {
            return &location->data;
        }
        return 0;
    }
    T* Next() {
        if (!location)
            return 0;
        location = location->node;
        if (location)
            return &location->data;
        return 0;
    }
private:
    fjxChainNode<T>* location;
};
//创建一个新的有序线性表C,该表中包含了A和B的所有元素。
template <class T>
void Merge(const myChain<T>& A, const myChain<T>& B, myChain<T>& C) {
    ChainIterator<T> a, b;//链表A,B的遍历器
    T* DataA = a.Initialize(A);//指向A中元素的指针
    T* DataB = b.Initialize(B);//指向B中元素的指针
    C.fjxErase();
    while (DataA && DataB)
    {
        if (*DataA <= *DataB)
        {
            C.fjxAppend(*DataA);
            DataA = a.Next();
        }
        else
        {
            C.fjxAppend(*DataB);
            DataB = b.Next();
        }
    }
    if (DataA)
        while (DataA)
        {
            C.fjxAppend(*DataA);
            DataA = a.Next();
        }
    else
        while (DataB)
        {
            C.fjxAppend(*DataB);
            DataB = b.Next();
        }
}

int main() {
    myChain<int>a;
    myChain<int>b;
    myChain<int>c;
    cout << "Input1" << endl;
    int num = -1;
    while (num != 0) {
        cin >> num;
        if (num != 0)
            a.fjxAutoNew(num);
    }
    cout << "Output1" << endl;
    cout << a;
    cout << "Input2" << endl;
    cin >> num;
    a.fjxAutoNew(num);
    cout << "Output2" << endl;
    cout << a;
    cout << "Input3" << endl;
    cin >> num;
    cout << "Output3" << endl;
    cout << a.fjxSearch(num) << endl;
    cout << "Input4" << endl;
    cin >> num;
    cout << "Output4" << endl;
    cout << a.fjxSearch(num) << endl;
    cout << "Input5" << endl;
    num = -1;
    while (num != 0) {
        cin >> num;
        if (num != 0)
            b.fjxAutoNew(num);
    }
    cout << "Output5" << endl;
    cout << b;
    Merge(a, b, c);
    cout << c;
    cout << "End" << endl;
    return 0;



}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值