C++之简单实现stack

mac2024-05-06  36

简介

stack是配接器:

一种用来修饰容器(containers) 或仿函式(functors) 或迭代器(iterators)接口的东西

stack在源码中底层是deque,由于deque还没写,刚写了list,就用list来实现stack。 环境:VS2017

list迭代器

#pragma once #include <iostream> using std::cout; using std::cerr; using std::endl; namespace HN { template<typename T> struct hn_list_node;//下边要用到,所以先声明,仅声明模板使用extern报错,原因未知 template<class T> class hn_list;//下边要用到,所以先声明,仅声明模板使用extern报错,原因未知 //const迭代器 template<typename T> class const_iterator { public: friend class hn_list<T>;//设置友元以访问hn_list const_iterator() :current(NULL) { } const T& operator*() const { return current->node; } const_iterator & operator++(int) { const_iterator old = *this; ++(*this); return old; } const_iterator & operator++() { current = current->next; return *this; } bool operator == (const const_iterator & rhs) const { return current == rhs.current ? true : false; } bool operator != (const const_iterator & rhs) const { return !(current == rhs.current); } hn_list_node<T> * operator -> () { return current; } ~const_iterator() { } protected: hn_list_node<T> * current; T& retrieve() const//恢复,即得到节点 { return current->node; } private: }; //普通迭代器,继承自cosnt迭代器 template<typename T> class iterator : public const_iterator<T> { public: friend class hn_list<T>;//设置友元以访问hn_list iterator() { } //非const默认调用此版本 const T& operator * () { //cout << "调用非const版本operator *()" << endl; return const_iterator<T>::current->node; } //可以看到根据是否为const对象函数可以实现重载,const对象调用此版本 const T& operator * () const { //cout << "调用const版本operator *()" << endl; return const_iterator<T>::operator *(); } iterator& operator++()//前置自增 { const_iterator<T>::current = const_iterator<T>::current->next; return *this; } iterator& operator++(int)//后置自增 { iterator old = *this; ++(*this); return old; } ~iterator() { } }; }

list实现

#pragma once #include "hn_iterator.h" namespace HN { //template<typename T> class const_iterator; //template<typename T> class iterator; //链表节点 template<typename T> struct hn_list_node { hn_list_node<T> * pre; hn_list_node<T> * next; T node; hn_list_node() :pre(nullptr), next(nullptr) { } hn_list_node(const T & obj) :node(obj), pre(nullptr), next(nullptr) { } }; //链表 template<class T> class hn_list { public: typedef const_iterator<T> const_iterator;//简化 typedef iterator<T> iterator;//简化 hn_list() :head_node_ptr(new hn_list_node<T>()), tail_node_ptr(new hn_list_node<T>()), theSize(0) { cout << "进入hn_list无参构造" << endl; head_node_ptr->next = tail_node_ptr; tail_node_ptr->pre = head_node_ptr; } hn_list(int size) :head_node_ptr(new hn_list_node<T>()), tail_node_ptr(new hn_list_node<T>()), theSize(size) { cout << "进入hn_list指定大小构造" << endl; head_node_ptr->next = tail_node_ptr; tail_node_ptr->pre = head_node_ptr; for (int i = 0; i < theSize; i++) { hn_list_node<T> * tmp = new hn_list_node<T>(); tail_node_ptr->pre->next = tmp; tmp->pre = tail_node_ptr->pre; tmp->next = tail_node_ptr; tail_node_ptr->pre = tmp; } } const_iterator begin() const { const_iterator it; it.current = head_node_ptr->next; return it; } const_iterator end() const { const_iterator it; it.current = tail_node_ptr; return it; } iterator begin() { iterator it; it.current = head_node_ptr->next; return it; } //拷贝构造函数 hn_list(const hn_list<T> & rhs) :head_node_ptr(new hn_list_node<T>()), tail_node_ptr(new hn_list_node<T>()), theSize(rhs.theSize) { cout << "进入hn_list拷贝构造" << endl; head_node_ptr->next = tail_node_ptr; tail_node_ptr->pre = head_node_ptr; for (const_iterator it = rhs.begin(); it != rhs.end(); it++) { push_back(*it); } } void push_back(const hn_list_node<T>& rhs) { hn_list_node<T> *tmp = new hn_list_node<T>(rhs); tail_node_ptr->pre->next = tmp; tmp->pre = tail_node_ptr->pre; tmp->next = tail_node_ptr; tail_node_ptr->pre = tmp; ++theSize; } void push_front(const T& rhs) { hn_list_node<T> * tmp = new hn_list_node<T>(rhs); head_node_ptr->next->pre = tmp; tmp->next = head_node_ptr->next; head_node_ptr->next = tmp; tmp->pre = head_node_ptr; ++theSize; } void pop_front() { if (empty()) return; hn_list_node<T> * tmp = head_node_ptr->next; head_node_ptr->next = tmp->next; tmp->next->pre = head_node_ptr; delete tmp; --theSize; } void pop_back() { if (empty()) return; hn_list_node<T>* tmp = tail_node_ptr->pre; tmp->pre->next = tail_node_ptr; tail_node_ptr->pre = tmp->pre; delete tmp; --theSize; } bool empty() { return theSize == 0 ? true : false; } void clear() { while (!empty()) { pop_back(); } } void resize(int num) { if (num == theSize) { return; } else if (num > theSize) { int n = num - theSize; for (int i = 0; i < n; i++) { push_back(T()); } } else { int n = theSize - num; for (int i = 0; i < n; i++) { pop_back(); } } } T& front() { return head_node_ptr->next->node; } T& back() { return tail_node_ptr->pre->node; } int size()const { return theSize; } //应再实现一个iterator版本 void insert(const_iterator it, const T& rhs) { hn_list_node<T> * tmp = it.current; hn_list_node<T> * new_node = new hn_list_node<T>(rhs); tmp->pre->next = new_node; new_node->pre = tmp->pre; new_node->next = tmp; tmp->pre = new_node; ++theSize; } //只删除第一个相等的节点 void remove(const T& rhs) { if (empty()) return; else { for (iterator it = begin(); it != end(); it++) { if (*it == rhs) { cout << "remove " << *it << endl; hn_list_node<T> * tmp = it.current; tmp->next->pre = tmp->pre; tmp->pre->next = tmp->next; delete tmp; --theSize; return;//已经remove了,应当返回,因为迭代器已经失效了 } } } } //此处返回hn_list<T>&,用以支持连等,即ld = lc = lb; //也可以返回void const hn_list<T>& operator = (const hn_list<T>& rhs) { cout << "进入赋值运算符" << endl; if (this == &rhs) { return *this; } else { this->clear(); hn_list::const_iterator it = rhs.begin(); for (; it != rhs.end(); it++) { push_back(*it); } return *this; } } //仅仅为了测试写的,便于查看各个元素 void show() { hn_list_node<T> * tmp = head_node_ptr->next; while (tmp!=tail_node_ptr) { cout << tmp->node << " "; tmp = tmp->next; } cout << endl; } bool operator == (const hn_list<T> & rhs) { if (this == &rhs) { return true; } else if(theSize==rhs.theSize) { hn_list::const_iterator itl = begin(); hn_list::const_iterator itr = rhs.begin(); while (itl!=end() && itr!=rhs.end()) { if (itl.current->node != itr.current->node) { return false; } itl++; itr++; } return true; } else { return false; } } ~hn_list() { cout << "进入hn_list析构" << endl; if (head_node_ptr != NULL) delete head_node_ptr; if (tail_node_ptr != NULL) { delete tail_node_ptr; } } protected: hn_list_node<T> * head_node_ptr; hn_list_node<T> * tail_node_ptr; int theSize; }; }

stack实现

#pragma once #include <iostream> #include "hn_list.h" using std::cout; using std::cerr; using std::endl; using namespace HN; namespace HN { //此处默认传入我自己写的list,也可以传入std::list template<typename T,class hn_List=hn_list<T>> class hn_stack { public: hn_stack() { cout << "进入hn_stack无参构造函数" << endl; } ~hn_stack() { } void clear() { return list.clear(); } bool empty() { return list.empty(); } int size() const { return list.size(); } void push(T t) { list.push_back(t); } void pop() { if (list.empty()) { cerr << "栈已空!!!"; return; } else { list.pop_back(); } } T& top() { return list.back(); } void show() { list.show(); } bool operator == (const hn_stack<T, hn_List> & rhs) { return list == rhs.list; } protected: hn_List list; }; }

测试代码

#include "pch.h" #include "hn_stack.h" #include <stack> using namespace std; int main() { std::cout << "Hello World!\n"; hn_stack<int> sa; sa.push(1); sa.push(3); sa.push(5); cout << "sa.empty(): " << (true==sa.empty()?"true":"false") << endl; cout << "sa.size(): " << sa.size() << endl; sa.show(); sa.pop(); sa.pop(); sa.pop(); sa.pop(); sa.show(); sa.push(1); sa.push(3); sa.push(5); sa.push(1); sa.push(3); sa.push(5); sa.show(); cout<<"sa.top(): "<<sa.top() << endl; sa.top()++; cout << "sa.top(): " << sa.top() << endl; sa.clear(); cout << "after clear:-------------------------------------------------" << endl; cout << "sa.empty(): " << (true == sa.empty() ? "true" : "false") << endl; cout << "sa.size(): " << sa.size() << endl; sa.push(1); sa.push(3); sa.push(5); sa.push(1); sa.push(3); sa.push(5); cout << "sa.size(): " << sa.size() << endl; sa.show(); hn_stack<int> sb; sb.push(1); sb.push(3); sb.push(5); sb.push(1); sb.push(3); sb.push(5); cout << "sb.size(): " << sb.size() << endl; sb.show(); cout << "sa==sb? : " << (sa == sb?"true":"false") << endl; cout << "TEST END!!!" << endl; }

测试结果

总结

list的实现略有修改,所以此处再次贴出。 stack实现了基本功能,符合预期。

最新回复(0)