/*
1.模板也可以使用默认参数
2.构造函数有个初始化列表,即便我们不写,对于自定义类型,他也会进行初始化
3.stack与queue使用适配器实现
*/
适配器是一种设计模式(设计模式是一套被反复使用的、多数人知晓的、经过分类编目的、代码设计经验的总 结),该种模式是将一个类的接口转换成客户希望的另外一个接口。
假设你有一台笔记本电脑,但它只有 USB 接口,而你需要连鼠标、键盘、HDMI 显示器和有线网络。这时,你可以使用一个 USB 到多端口适配器来连接所有的设备,使它们都可以通过 USB 接口使用。这个适配器就像一个接口转换器,把原本不兼容的接口给转换成兼容的接口,这就是适配器的作用。在软件开发中,适配器模式也是这个道理,它帮助将两个不兼容的接口或类进行转换,使它们可以一起工作。
现在通过实现stack与queue来感受适配器
栈是一种后进先出的结构,在实现时,我们可以对vector进行包装,将其包装为stack
vector的push_back可以看作stack的入栈
vector的pop_back可以看作stack的出栈
vector的back()获取尾部数据,可以看作stack获取栈顶元素
vector的empty()可以用来判断stack是否为空。
由此可见,stack的所有功能在vector中已经可以实现,所以,我们可以使用vector来实现stack。
对vector的包装,适配器
代码:
template<class T>
class stack {
public:
stack() {
//question1
}
void push_back(const T&val) {
_c.push_back(val);
}
void pop_back(const T&val) {
_c.pop_back();
}
T& Top() {
return _c.back();
}
const T& top() const{
return _c.back();
}
bool empty() const{
return _c.empty();
}
private:
std::vector<T> _c;
};
思考:
question1处,需不需要添加如下代码: _c = std::vector<T>(); ?
不需要,构造函数有个初始化列表,即便我们不写,对于自定义类型,他也会进行初始化。
实际上,不仅仅vector可以实现stack,只要我们进行包装的底层支持以上几种操作都可以,所以list也可以实现
底层容器可以是标准容器类模板之一,也可以是其他专门设计的容器类。
该底层容器应至少支持以下操作:
empty:检测队列是否为空
size:返回队列中有效元素的个数
front:返回队头元素的引用
back:返回队尾元素的引用
push_back:在队列尾部入队列
pop_front:在队列头部出队列
为了使包装更为广泛
我们可以把底层容器换成模板参数,使得我们能根据自己的需要选择使用哪种容器
template<class T,class Container=std::vector<T>>//question1
class stack {
public:
stack() {
}
void push_back(const T&val) {
_c.push_back(val);
}
void pop_back(const T&val) {
_c.pop_back();
}
T& Top() {
return _c.back();
}
const T& top() const{
return _c.back();
}
bool empty() const{
return _c.empty();
}
private:
std::Container _c;
};
在question1处,class Container=std::vector<T>,模板也可以使用默认参数