1

假设我有一个模板函数,它通过指向成员的指针在结构中设置数据:

struct S
{
    double d;
    unsigned int u;
};

struct A
{
    S s, s2;
    float f;
    int i;
};

template<typename Stream, typename Class, typename Type>
void read(Stream& s, Class& out, Type Class::*member)
{
    s >> out.*member;
}

现在对于像这样的普通成员fa我可以在以下任意实例上使用此函数struct A

#include <sstream>

int main(int, char**)
{
    std::stringstream stream;

    A a;
    stream.clear(); stream.str("1");
    read(stream, a, &A::i);
    stream.clear(); stream.str("1.5");
    read(stream, a, &A::f);
    stream.clear(); stream.str("2");

    printf("%i\n", a.i);
    printf("%f\n", a.f);
}

但是,有没有办法在不为每个复合成员( 、 等)编写新的、有效相同的函数的情况下访问成员或A::sA::s2类似方式访问成员?据我所知,指向成员成员的指针不存在,但是否有替代解决方案?(它必须在or的任意实例上工作,类似于上面的指向成员的解决方案的工作方式,并且不应该在or中需要额外的方法)。ss2structclassAS

为了稍微澄清这个问题(另请参阅此答案中的评论):在实际代码(配置文件阅读器)中,调用者使用第一个字符串在地图中进行查找,实际上并不知道当前正在读取什么(使用第二个字符串),因为指向成员的参数是绑定的。此外,映射被初始化一次并用于 的多个实例A,因此是指向成员的指针。

请注意 c++03 标签。因此,c++11 lambdas 不是一个选项。

4

1 回答 1

1

不确定我是否解决了问题。正如您可以使用 PTM 访问成员 i、f 一样,您可以对 S 执行相同操作。您不需要单独的函数来访问 s 和 s2:单个函数将使用额外的 type 参数S A::*

或者,如果类型必须是可变的,您可以扩展您的读取函数,例如:

template<typename Stream, typename Class, typename Type, typename Class2, typename Type2>
void read(Stream& s, Class& out, Type Class::*member, Type2 Class2::*member2)
{
    s >> ((out.*member).*member2);
} 

并像使用它一样read(stream, a, &A::s, &S::u);

(我手头没有编译器来测试它,它可能需要一些修饰)

于 2013-06-04T23:48:00.707 回答