write in advance
重写stack类,加上operator= function 与copy constructor,private中有指针,采用动态分配内存的方式。因此,实际上温习的是指针所指向内存的dynamic allocation,需要注意的是这两个函数。在类的private 中,Max表示对象在创建时最大能拥有的栈的元素值。top指向栈中元素的上一个位置。 size 是每个单独类中元素的数量大小,自然不能超过Max。
注意对单个栈是否满的判断采用的是 top== size。
implementation
head file stack2.h
#ifndef STACK2_H_
#define STACK2_H_
#include<iostream>
typedef unsigned long Item;
class Stack
{
private:
enum { Max = 10 };
Item* pitems;
int size;
int top;
public:
Stack(int n = Max);
~Stack();
Stack(const Stack& st);
bool isempty() const;
bool isfull() const;
bool push(const Item& item);
bool pop(Item& item);
Stack& operator=(const Stack& st);
friend std::ostream& operator<<(std::ostream& os, Stack&);
};
#endif
method file
注意copy constructor 与 operator= 的区别。除了自我赋值的检查,copy constructor的调用对象困难未初始化,所以不能在copy constructor的函数中delete。相反,operator= 函数的两个对象都已经初始化,在排除自我赋值的后,需要delete。
#include"stack2.h"
Stack::Stack(int n)
{
size = n;
top = 0;
pitems = new Item[size];
}
Stack::~Stack()
{
delete[] pitems;
}
bool Stack::isempty() const
{
return top == 0;
}
bool Stack::isfull() const
{
return top == size;
}
bool Stack::push(const Item& item)
{
if (!isfull())
{
pitems[top++] = item;
return true;
}
else
{
std::cout << "full already\n";
return false;
}
}
bool Stack::pop(Item& item)
{
if (!isempty())
{
item = pitems[--top];
return true;
}
return false;
}
Stack::Stack(const Stack& st): size(st.size), top(st.top)
{
pitems = new Item[st.size];
for (int i = 0; i < top; i++)
pitems[i] = st.pitems[i];
}
Stack& Stack::operator=(const Stack& st)
{
if (this == &st)
{
return *this;
}
delete[] pitems;
size = st.size;
top = st.top;
pitems = new Item[size];
for (int i = 0; i < top; i++)
{
pitems[i] = st.pitems[i];
}
return *this;
}
std::ostream& operator<<(std::ostream& os, Stack& st)
{
for (int i = 0; i < st.top; i++)
os << st.pitems[i] << " ";
os << std::endl;
return os;
}
test file
#include"stack2.h"
#include<iostream>
int main()
{
Stack obj1(5);
obj1.push(3);
obj1.push(2);
obj1.push(66);
Stack obj2(obj1);
Item temp;
for (int i = 0; i < 3; i++)
{
obj2.pop(temp);
std::cout << temp << " ";
}
std::cout << std::endl;
std::cout << obj2.isempty() << std::endl;
obj2 = obj1;
std::cout << obj2;
return 0;
}
summary
此次练习复习了copy constructo 与 operator= 两个函数在动态分配内存时需要注意的操作事项。再次注意到copy constuctor 与 operator= 的不同的。
当然,我们也复习了stack数据结构,top始终指向栈顶元素的上一个位置。它与顺序表的比较,copy constructor 与 operator= 具体实现的比较,都有利于加深印象和理解。