我知道有人会说这是对象切片问题,但我认为不是。我在这个网站上看过很多相关帖子,但不太一样。让我们从代码开始:
#include "stdafx.h"
#include <list>
struct MY_STRUCT
{
int a;
int b;
};
class File
{
public:
virtual void Load(char * fileName) = 0;
};
class ExcelFile : public File
{
protected:
std::list<MY_STRUCT> my_list;
public:
ExcelFile(){};
~ExcelFile(){};
virtual void Load(char * fileName)
{
// load the file into my_list
}
};
int _tmain(int argc, _TCHAR* argv[])
{
char fileName[] = "test.txt";
File * file = new ExcelFile;
file->Load( fileName );
// Now I need to fill a Windows List or CListView from my_list data but how?
// I can't access or iterate my_list here and I am not too sure if
// should pass a windows object to the class to fill it up?
// Even if I iterate by adding a member function to return the list object, wouldn't not
// it violate the data encapsulation rule thereby defeating the purpose of having
// interface class?
return 0;
}
所以基本上我有一个接口类,其派生类具有聚合(集合)中的数据。现在我想显示数据。这样做的正确方法是什么?我已经在代码中的注释中提到了这个问题......我想我在写这篇文章时找到了答案,我应该让类添加填充列表的函数。我想如果我必须填充ListBox或ListView,那么每个列表需要两个函数。我想知道我是否可以通过访客模式做得更好!?
答案 0 :(得分:1)
没有出现(如果我理解你的问题)对对象拼接有任何担心。看起来您要做的就是查看“聚合”类中的列表,在这种情况下:ExcelFile()
向ExcelFile()
添加一个方法,可能类似于print()
,或者如果您想获得幻想:
std::ostream & operator<<(std::ostream &os) {
std::list<MY_STRUCT>::iterator it;
for (it = my_list.begin(); it != my_list.end(); ++it) {
os << "A: " << it.a << ", B: " << it.b << std::endl;
}
return os;
}
注意:代码尚未编译或运行,它只是一个指导原则。
修改强>
如果OP希望在其他地方使用他的列表,则返回对集合的常量引用:
const std::list<MY_STRUCT> & getSet() const {
return my_list;
}
答案 1 :(得分:0)
只需为您的my_list
成员提供至少一个getter,以便从课堂外安全访问(不会违反任何封装规则!):
class ExcelFile
{
public:
// ...
const std::list<MY_STRUCT>& getMyList() const { return my_list; }
// ...
}