C ++:动态访问类属性

时间:2010-09-13 09:53:54

标签: c++ templates attributes dynamic-data

我想知道是否可以在不知道运行时访问的属性名称的情况下动态访问类的属性。

为了让您更好地了解我的目标,这个PHP代码应该展示我想要做的事情:

<?php
$object = new object();
$property = get_name_out_of_textfile();
echo $object->$property;
?>

我知道不可能做同样的事情,但是假设我在std :: string的cstring中得到了一个属性的名称,并希望访问与该名称匹配的属性。有没有办法做到这一点?

背景是我想从具有大量属性的类动态加载和保存数据。我可以保存我想要的任何格式,但我需要一种方法来重新加载它们,而不是每次都指定确切的属性。

提前感谢您的帮助, 罗宾。

3 个答案:

答案 0 :(得分:5)

基本上,您需要创建一个额外的函数ala:

std::string get(const std::string& field, const std::string& value_representation)
{
    std::ostringstream oss;
    if (field == "a")
        oss << a;
    else if (field == "b")
        oss << b;
    else
        throw Not_Happy("whada ya want");
    return oss.str();
}

有许多现有的框架可以做到这一点,例如boost序列化库。大多数涉及使用某种标记声明您的类,或者更糟糕的是 - 使用二次元数据来定义。

如果你真的需要一些侵入性较小的东西,那么像Gcc-XML和OpenC ++这样的工具可以让你自动生成这些函数(前者可以轻松地与XML库,一个小python或ruby结合使用,方便但是低绩效胜利。)

为了绝对清楚,C ++没有提供任何符合标准的自动化方法。没有受欢迎的编译器为此提供扩展。在解压缩中,您可以在某处解析自己的调试信息,但绝对不建议这样做。

答案 1 :(得分:2)

如果序列化是您主要关注的问题,请查看Boost.Serialization等现有解决方案,这些解决方案会选择流媒体方式:

// save data to archive:
// create and open a character archive for output
std::ofstream ofs("filename");
boost::archive::text_oarchive oa(ofs);
// write class instance to archive
oa << myInstance;

// ...

// restore data from archive:
// create and open an archive for input
std::ifstream ifs("filename");
boost::archive::text_iarchive ia(ifs);
// read class state from archive
ia >> myInstance;

答案 2 :(得分:2)

是的,可能...... Python,php等......是在C或C ++之上实现的,他们提供它。

但它也非常尴尬。

您要求的是在运行时检查类型的能力称为内省。这很难实现,所以考虑到你提出问题的方式......不要考虑它,你需要更多的经验。

如果你想要内省,那就想想另一种语言吧。