13.4节练习

练习13.33 为什么Message的成员save和remove的参数是一个Folder&?为什么我们不将参数定义为Folder或是const Folder&?

目的是从Folder中添加/删除Message。

定义Floder添加/删除的是Message的副本,不是对象本身,而const Folder&将使得不能删除对象。


练习13.34 编写本节所描述的Message。

(见13.37)


练习13.35 如果Message使用合成的拷贝控制成员,将会发什么?

当使用合成的拷贝构造函数,在我们拷贝一个Message时,得到的副本应该是与Message出现在相同的Floder。

定义自己版本的拷贝构造函数,才能将拷贝的对象插入原来的Folder中。


练习13.36 设计并实现对应的Folder类。此类应该保存一个指向Folder中包含的Message的set。

(见13.37)


练习13.37 为Message类添加成员,实现向folders添加或删除一个给定的Folder*。这两个成员类似Folder类的addMsg和remMsg操做。

// = 。=

#include <set>
#include <string>
using namespace std;

class Folder;
class Message {
	friend class Folder;
	friend void swap(Message &, Message &);
public:
	explicit Message(const std::string &str = "") :contents(s) {}
	Message (const Message&);
	Message operator=(const Message&);
	~Message();
	void save(Folder&);
	void remove(Folder&);
private:
	std::string contents;
	std::set<Folder*> folders;
	void add_to_Folder(const Message&);
	void remove_from_Folder();
};

void Message::save(Folder& f)
{
	folders.insert(f);
	f.addMsg(this);
}
void Message::remove(Folder &f)
{
	folders.erase(f);
	f.remMsg(this);
}

void Message::add_to_Folder(const Message &m)
{
	for (auto f : m.folders) {
		f->addMsg(this);
	}
}
Message::Message(const Message&m) :contents(m.contents), folders(m.folders)
{
	add_to_Folder(m);
}

void Message::remove_from_Folder()
{
	for (auto f : folders) {
		f->remMsg(this);
	}
}
Message::~Message()
{
	remove_from_Folder();
}

Message& Message::operator=(const Message &rhs)
{
	remove_from_Folder();
	contents = rhs.contents;
	folders = rhs.folders;
	add_to_Folder(rhs);
	return *this;
}

void swap(Message &lhs, Message &rhs)
{
	for (auto f : lhs.folders) {
		f->remMsg(&lhs);
	}
	for (auto f : rhs.folders) {
		f->remMsg(&rhs);
	}
	swap(lhs.folders, rhs.folders);
	swap(lhs.contents, rhs.contents);
	for (auto f : lhs.folders) {
		f->addMsg(&lhs);
	}
	for (auto f : rhs.folders) {
		f->addMsg(&rhs);
	}
}

class Folder {
	friend void swap(Message&, Message&);
	friend class Message;
public:
	~Folder(); // remove self from Messages in msgs  
	Folder(const Folder&); // add new folder to each Message in msgs  
	Folder& operator=(const Folder&); // delete Folder from lhs messages  
									  // add Folder to rhs messages  
	Folder(Folder&&);   // move Messages to this Folder   
	Folder& operator=(Folder&&); // delete Folder from lhs messages  
								 // add Folder to rhs messages  

#ifdef DEFAULT_FCNS  
	Folder() = default; // defaults ok  
#else  
	Folder() { } // msgs will be default initialized, which is what we want  
#endif  

	void save(Message&);   // add this message to folder  
	void remove(Message&); // remove this message from this folder  

	void debug_print(); // print contents and it's list of Folders,   
private:
	std::set<Message*> msgs;  // messages in this folder  

	void add_to_Messages(const Folder&);// add this Folder to each Message  
	void remove_from_Msgs();     // remove this Folder from each Message  
	void addMsg(Message *m) { msgs.insert(m); }
	void remMsg(Message *m) { msgs.erase(m); }
	void move_Messages(Folder*); // move Message pointers to point to this Folder  
};


练习13.38 我们并未使用拷贝并交换方式来设计Message的赋值运算符。你认为原因是什么?

拷贝操作要分配内存,提高程序的不安全性。

交换操作对两个已存在的资源进行交换,优先考虑。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值