使用模版,灵活的使用构造函数来建立链表,注意看push操作,new以后条用HEAD的构造函数来插入链表,当前的head是新元素的next域,实现头插法,没使用头元素,可以自己实现,当然也可以使用尾插法来实现这样的链表
重载了++运算符,也可以使用iterator来实现。这样在使用的时候不需要直接操作链表,使用模版对象的引用就可以达到在链表中移动的作用,如果实现双链表和--/-=/+=....的重载,这个链表就更完美了
同时更重要的是大家可以看到多个模版对象指向同一区域的时候,怎样才能避免一个对象在脱离作用的之前的操作不会影响到另一个对象的使用
st不拥有存放在它里面的string对象,st_own是实际存放的主容器
string 最好能替换成用户类型的对象,这样测试就更明显了
头文件
#ifndef _STACK_HEAD
#define _STACK_HEAD
template < class T > class Stack
... {
private:
typedef struct Link...{
T* data;
Link* next;
Link(T* data,Link* next):data(data),next(next)...{}
}*HEAD;
HEAD head,rhead;
bool own;
int count;
public:
Stack(bool own=true):head(NULL),own(own)...{count=0;}
~Stack(void);
void push(T* data)
...{
head=new Link(data,head);//新建并插入元素
if(!head)exit(0);
count++;rhead=head;
}
T* peek()const...{
return head?head->data:NULL;
}
T* pop();
void Head()...{head=rhead;}
bool owns() const...{return own;}
void owns(bool ownparam)...{own=ownparam;}
operator bool()const...{return head!=NULL;}
const Stack<T>& operator++(int)...{//postfix
if(!head)return NULL;
head=head->next;
return *this;
}
const int size()...{return count;}
//const T* FindElement()//
//const T* FindElement(int position)//
} ;
template < class T > T * Stack < T > ::pop()
... {
if(head==NULL)return NULL;
T* result=head->data;
Link* oldHead=head;
head=head->next;
delete oldHead;
return result;
}
template < class T > Stack < T > :: ~ Stack()
... {
if(!own)return;
while(!head)delete pop();
cout<<"Destruction called!!!"<<endl;
}
#endif
#define _STACK_HEAD
template < class T > class Stack
... {
private:
typedef struct Link...{
T* data;
Link* next;
Link(T* data,Link* next):data(data),next(next)...{}
}*HEAD;
HEAD head,rhead;
bool own;
int count;
public:
Stack(bool own=true):head(NULL),own(own)...{count=0;}
~Stack(void);
void push(T* data)
...{
head=new Link(data,head);//新建并插入元素
if(!head)exit(0);
count++;rhead=head;
}
T* peek()const...{
return head?head->data:NULL;
}
T* pop();
void Head()...{head=rhead;}
bool owns() const...{return own;}
void owns(bool ownparam)...{own=ownparam;}
operator bool()const...{return head!=NULL;}
const Stack<T>& operator++(int)...{//postfix
if(!head)return NULL;
head=head->next;
return *this;
}
const int size()...{return count;}
//const T* FindElement()//
//const T* FindElement(int position)//
} ;
template < class T > T * Stack < T > ::pop()
... {
if(head==NULL)return NULL;
T* result=head->data;
Link* oldHead=head;
head=head->next;
delete oldHead;
return result;
}
template < class T > Stack < T > :: ~ Stack()
... {
if(!own)return;
while(!head)delete pop();
cout<<"Destruction called!!!"<<endl;
}
#endif
测试的小程序:这样写链表很有意思
#include
<
string
>
#include < iostream >
using namespace std;
int _tmain( int argc, _TCHAR * argv[])
... {
Stack<string> st_own;
Stack<string> st(false);
for(int i=0;i<10;i++)
...{
//2个模版的元素都指向同一区域
string *temp=new string("helloworld");
st_own.push(temp);
if(i%2==0)st.push(temp);
}
//观察OwnerShip
while(st)
cout<<"st____call pop:"<<*st.pop()<<endl;
/**////输出所有的元素
Stack<string>& p=st_own;
while(p++)
...{
cout<<"element is: "<<*p.peek()<<endl;
}
system("PAUSE");
return 0;
}
#include < iostream >
using namespace std;
int _tmain( int argc, _TCHAR * argv[])
... {
Stack<string> st_own;
Stack<string> st(false);
for(int i=0;i<10;i++)
...{
//2个模版的元素都指向同一区域
string *temp=new string("helloworld");
st_own.push(temp);
if(i%2==0)st.push(temp);
}
//观察OwnerShip
while(st)
cout<<"st____call pop:"<<*st.pop()<<endl;
/**////输出所有的元素
Stack<string>& p=st_own;
while(p++)
...{
cout<<"element is: "<<*p.peek()<<endl;
}
system("PAUSE");
return 0;
}
添加上一些有用的功能就可以是一个很好的模版链表了