queue
queue同stack类似的设计,本身是一种单向出口的FIFO的数据结构
使用双向的数据结构都能实现,就如前面设计的list、deque
vector是尾部单向,可以做stack,但是不能做queue
list的 == 、!=存在问题,其他功能完好
deque可以实现,这里使用deque实现queue
queue设计
-
操作 比较和分配队列
-
empty() 队列为空则返回真
-
pop() 移除队头元素
-
push() 在队尾增加元素
-
size() 返回队列中元素数目
-
front() 返回队头元素
-
back() 返回队尾元素
stl_queue.h
#ifndef _QUEUE_H_
#define _QUEUE_H_
#include "../p2_STL_Source/stl_deque.h"
//#include "../p2_STL_Source/stl_list.h"
namespace mySTL {
// queue队列
// 双向开口的数据结构都能实现,你这里换deque、list(== != 需要改动)
template<class T, class Container = mySTL::deque<T>>
class queue {
public:
typedef T value_type;
typedef Container container_type;
typedef typename Container::reference reference;
typedef typename Container::const_reference const_reference;
typedef typename Container::size_type size_type;
private:
Container container_;
public:
// 构造函数
queue() {}
explicit queue(const container_type& ctnr) :container_(ctnr) {}
// 元素查看
bool empty() const { return container_.empty(); }
size_type size() const { return container_.size(); }
reference& front() { return container_.front(); }
const_reference& front() const { return container_.front(); }
reference& back() { return container_.back(); }
const_reference& back() const { return container_.back(); }
// 元素操作
void push(const value_type& val) { container_.push_back(val); }
void pop() { container_.pop_front(); }
void swap(queue& x) { container_.swap(x.container_); }
public:
template <class T, class Container>
friend bool operator== (const queue<T, Container>& lhs, const queue<T, Container>& rhs);
template <class T, class Container>
friend bool operator!= (const queue<T, Container>& lhs, const queue<T, Container>& rhs);
template <class T, class Container>
friend void swap(queue<T, Container>& x, queue<T, Container>& y);
};
template <class T, class Container>
bool operator== (const queue<T, Container>& lhs, const queue<T, Container>& rhs) {
return lhs.container_ == rhs.container_;
}
template <class T, class Container>
bool operator!= (const queue<T, Container>& lhs, const queue<T, Container>& rhs) {
return lhs.container_ != rhs.container_;
}
template <class T, class Container>
void swap(queue<T, Container>& x, queue<T, Container>& y) {
mySTL::swap(x.container_, y.container_);
}
}
#endif
stl_queue_test.h
#ifndef _QUEUE_TEST_H_
#define _QUEUE_TEST_H_
#include "../p2_STL_Source/stl_queue.h"
#include <queue>
#include <cassert>
#include <string>
namespace mySTL
{
namespace queueTest
{
template<class T>
using stdQ = std::queue < T >;
template<class T>
using myQ = mySTL::queue < T >;
void test01();
void test02();
void test03();
void test04();
void test05();
}
}
#endif
stl_queue_test.cpp
#include "stl_queue_test.h"
#include <iostream>
using namespace std;
namespace mySTL
{
namespace queueTest
{
void test01()
{
stdQ<int> q1;
myQ<int> q2;
for (auto i = 0; i != 10; ++i) {
q1.push(i);
q2.push(i);
}
for (auto i = 0; i != 10; ++i) {
cout << q1.front() << "\t" << q2.front() << endl;
q1.pop();
q2.pop();
}
}
void test02()
{
myQ<std::string> q;
cout << "is empty: " << boolalpha << q.empty() << endl;
cout << "size : " << q.size() << endl;
q.push("front");
q.push("back");
cout << q.front() << endl;
cout << q.back() << endl;
cout << "is empty: " << boolalpha << q.empty() << endl;
cout << "size : " << q.size() << endl;
}
void test03()
{
myQ<int> q1;
for (auto i = 0; i != 10; ++i)
q1.push(i);
cout << "size1 : " << q1.size() << endl;
auto q2(q1);
cout << "size2 : " << q2.size() << endl;
cout << "is equal: " << boolalpha << (q1 == q2) << endl;
cout << "is not equal: " << boolalpha << (q1 != q2) << endl;
}
void test04()
{
myQ<int> q1, q2;
q1.push(1); q1.push(2); q1.push(3);
q2.push(1); q2.push(2);
cout << "size1 is 3 : " << q1.size() << endl;
cout << "size2 is 2 : " << q2.size() << endl;
q1.swap(q2);
cout << "size1 is 2 : " << q1.size() << endl;
cout << "size2 is 3 : " << q2.size() << endl;
mySTL::swap(q1, q2);
cout << "size1 is 3 : " << q1.size() << endl;
cout << "size2 is 2 : " << q2.size() << endl;
}
void test05()
{
}
}
}