单向链表的C++ 模板

1.模板文件 t_list_unidir

#include <iostream>

#ifndef NULL
#define NULL ((void*)0) 
#endif

//链表节点模板类 
template <typename T>
class list_unidir
{
public:
	T m_data;
	list_unidir * p_next;
};

/*****************************************************************
*函数名:
*list_unidir<T> *list_unidir_create(const list_unidir<T> *)
*功能:
*创建一个单向链表 
*参数:
*指定类型的指针 
*返回值:
*链表头的指针
*说明:
*无 
*****************************************************************/ 
template <typename T>
list_unidir<T> * list_unidir_create(const list_unidir<T> *)
{
	list_unidir<T> * p_head = new list_unidir<T> ;
	if(!p_head)
		return NULL;
	p_head->p_next = NULL;
	return p_head;
}

/*****************************************************************
*函数名:
*void list_unidir_destroy(list_unidir<T> *p_head)
*功能:
*销毁一个单向链表 
*参数:
*链表头的指针 
*返回值:
*空
*说明:
*删除链表,释放内存空间 
*****************************************************************/ 
template <typename T>
void list_unidir_destroy(list_unidir<T> *p_head)
{
	list_unidir<T> * p_node ;
	while(p_head)
	{
		p_node = p_head ->p_next;
		delete p_head ;
		p_head = p_node ;
	}
}

/*****************************************************************
*函数名:
*bool list_unidir_push(
*	list_unidir<T> *p_head, const T &node_value)
*功能:
*向单向链表中压入数据 
*参数: 
*p_head~链表头的指针 ; node_value~节点值变量的引用 
*返回值:
*bool值指示操作是否成功 
*说明:
*无 
*****************************************************************/ 
template <typename T>
bool list_unidir_push(
	list_unidir<T> *p_head, const T & node_value)
{
	list_unidir<T> * p_node ;
	if(!p_head )
		return false;
	p_node = new list_unidir<T> ;
	if(!p_node)
		return false ;
	p_node ->m_data = node_value ;
	p_node ->p_next = p_head ->p_next;
	p_head ->p_next = p_node;
	return true ;
}

/*****************************************************************
*函数名:
*bool  list_unidir_del_node(
*	const list_unidir<T> *p_head, list_unidir<T> *p_node)
*功能:
*从单向链表中删除数据节点 
*参数: 
*p_head~链表头的指针 ; p_node~指定待删节点的指针 
*返回值:
*bool值指示操作是否成功 
*说明:
*无 
*****************************************************************/ 
template <typename T>
bool list_unidir_del_node(
	list_unidir<T> *p_head, list_unidir<T> *p_node)
{
	list_unidir<T> *p_prev = p_head ;
	if(!p_head)
		return false;
	while(p_prev && p_prev->p_next != p_node)
		p_prev = p_prev -> p_next ;
	//Not found ,return NULL 
	if(!p_prev)
		return false;
	p_prev ->p_next = p_node ->p_next ;
	delete p_node ;
	p_node = NULL ;
	return true ;
}

/*****************************************************************
*函数名:
*list_unidir<T> * list_unidir_find_node(
*	const list_unidir<T> *p_head,const T & node_value)
*功能:
*从单向链表中删除数据节点 
*参数: 
*p_head~链表头的指针 ; node_value~待比较节点值 
*返回值:
*指向查找到的节点的指针 
*说明:
*如果操作失败,那么返回一个无效指针NULL 
*****************************************************************/ 
template <typename T>
list_unidir<T> * list_unidir_find_node(
	const list_unidir<T> *p_head,const T & node_value)
{
	list_unidir<T> *p_node = p_head ->p_next;
	while(p_node)
		if((p_node ->m_data) == node_value) 
			return p_node ;
		else
			p_node = p_node -> p_next ;
	return NULL ;
}

/*****************************************************************
*函数名:
*bool list_unidir_copy_node(
*	const list_unidir<T> *p_node,T * value_addr)
*功能:
*从单向链表中拷贝数据节点到外部 
*参数: 
*p_node~指定待拷贝节点的指针 ; value_addr~用来接收数据的变量地址 
*返回值:
*bool值指示操作是否成功 
*说明:
*无 
*****************************************************************/ 
template <typename T>
bool list_unidir_copy_node(
	const list_unidir<T> *p_node,T * value_addr)
{
	if(!p_node || !value_addr)
		return false;
	*value_addr = p_node ->m_data ;
	return true ;
}

/*****************************************************************
*函数名:
*bool list_unidir_pop(
*	list_unidir<T> *p_head,T * value_addr)
*功能:
*从单向链表中弹出数据 
*参数: 
*p_head~链表头指针 ; value_addr~用来接收数据的变量地址 
*返回值:
*bool值指示操作是否成功 
*说明:
*无 
*****************************************************************/ 
template <typename T>
bool list_unidir_pop(
	list_unidir<T> *p_head,T * value_addr)
{
	list_unidir<T> *p_node ;
	if(!p_head ||!p_head->p_next||!value_addr)
		return false;
	p_node = p_head ->p_next ; 
	*value_addr = p_node ->m_data ;
	
	p_head->p_next = p_node ->p_next ;
	delete p_node ;
	p_node = NULL;
	return true ;
}

/*****************************************************************
*函数名:
*void list_unidir_traverse(
*	const list_unidir<T> *p_head)
*功能:
*遍历链表/输出每个节点 
*参数: 
*p_head~链表头指针
*返回值:
*无
*说明:
*如果要调用此方法,必须保证类型T支持输出重定向操作符 << 
*****************************************************************/ 
template <typename T>
void list_unidir_traverse(
	const list_unidir<T> *p_head)
{
	while(p_head = p_head ->p_next)
	{
		std::cout <<p_head<<std::endl;
	}
}


2.测试文件 test.cpp

#include <iostream>
#include <string>
#include "t_list_unidir"

using namespace std;

//一个简单的 用于测试模板链表的类 
class CA
{
	private:
		string m_str;
	public:
		CA(const string &s):m_str(s){}
		CA(){m_str = "";}
		void set_string(const string &s){m_str=s;} 
		string get_string()const {return m_str;}
		
		//拷贝节点所必需支持的重载函数 
		CA & operator=(const CA &k)
		{
			m_str = k.m_str;
		}
};

//遍历链表所必需支持的重载函数 
ostream & operator<<(ostream &os,const CA &s)
{
	os << s.get_string() ; 
}

//查找节点所必需支持的重载函数 
bool operator==(const CA &k,const CA &s)
{
	string k1 = k.get_string();
	string s1 = s.get_string();
	return k1==s1 ;
}

int main()
{
	const string c_s[4]={
		"Hello world!",
		"This is a sentence.",
		"Oh my God!",
		"Really ?"
	};
	list_unidir<CA> *l_ca;
	l_ca = list_unidir_create(l_ca);
	for(int k = 0;k<4;k++)
	{
		list_unidir_push(l_ca,CA(c_s[k]));
		cout << "PUSH:"<<c_s[k]<<endl;
	}
	string *ps,s("This is a sentence.");
	list_unidir<CA> *p_node ;
	p_node = list_unidir_find_node(l_ca,CA(s));
	if(p_node)
		cout <<"FIND:"<<(p_node ->m_data).get_string()<<endl
			<<"with:"<<s<<endl;
	
	if(p_node)
	{
		CA *p_tmp = new CA ;
		if(!list_unidir_copy_node(p_node,p_tmp))
			cerr << "Find Ok,but copy error!"<<endl;
		else
		{
			cout << p_tmp->get_string()<<endl; 
			p_tmp->set_string("hello world!");
			cout << p_tmp->get_string()<<endl; 
			cout <<"Copy out class from list OK!"<<endl;
		}
		delete p_tmp;
	}
	list_unidir_traverse(l_ca);
	if(p_node)
	{
		cout << "Now ,trying to delete node :"<<(p_node->m_data).get_string()<<endl;
		if(!list_unidir_del_node(l_ca,p_node))
			cerr << "Delete Node Failure !"<<endl;
	}
	list_unidir_traverse(l_ca);
	CA* p_t=new CA;
	do
	{
		if(!list_unidir_pop(l_ca,p_t))
			break;
		else
			cout <<"POP :"<<p_t->get_string()<<endl;
	}
	while(true);
	list_unidir_destroy(l_ca);
	return 0;
}



 

面向对象程序设计课程作业 1. 请创建一个数据类型为T的链表模板List,实现以下成员函数: 1) 默认构造函数List(),将该链表初始化为一个链表(10分) 2) 拷贝构造函数List(const List& list),根据一个给定的链表构造当前链表(10分) 3) 析构函数~List(),释放链表中的所有节点(10分) 4) Push_back(T e)函数,往链表最末尾插入一个元素为e的节点(10分) 5) operator<<()友元函数,将链表的所有元素按顺序输出(10分) 6) operator=()函数,实现两个链表的赋值操作(10分) 7) operator+()函数,实现两个链表的连接,A=B+C(10分) 2. 请编写main函数,测试该类模板的正确性: 1) 用List模板定义一个List类型的模板类对象int_listB,从键盘读入m个整数,调用Push_back函数将这m个整数依次插入到该链表中;(4分) 2) 用List模板定义一个List类型的模板类对象int_listC,从键盘读入n个整数,调用Push_back函数将这n个整数依次插入到该链表中;(4分) 3) 用List模板定义一个List类型的模板类对象int_listA,调用List的成员函数实现A = B + C;(4分) 4) 用cout直接输出int_listA的所有元素(3分) 5) 用List模板定义List类型的模板类对象double_listA, double_listB, double_listC,重复上述操作。(15分) 3. 输入输出样例: 1) 输入样例 4 12 23 34 45 3 56 67 78 3 1.2 2.3 3.4 4 4.5 5.6 6.7 7.8 2) 输出样例 12 23 34 45 56 67 78 1.2 2.3 3.4 4.5 5.6 6.7 7.8
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

sanzhong104204

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值