Com*_* 10 3 c++ pointers function
我正在查看一些已被移植并且无法编译的代码.代码以类似"C"的方式编写,并传递函数指针以便在对象上设置特定的mutator.正在填充的对象声明如下:
class Person
{
std::string n_;
int a_;
public:
void name( const std::string& n ) { n_ = n; }
std::string name() const { return n_; }
void age( const int& a ) { a_ = a; }
int age() const { return a_; }
};
Run Code Online (Sandbox Code Playgroud)
相当标准的东西.然后我们有一些有趣的功能,我为了简洁而修剪了它们:
typedef void (Person::FnSetStr)(const std::string& s);
typedef void (Person::FnSetInt)(const int& i);
void setMem( const std::string& label, Person* person, FnSetStr fn)
{
// Do some stuff to identify a std::string within a message from the label.
// assume that 'val_s' contains the string value of the tag denoted by
// the label.
(person->*fn)(val_s);
}
void setMem( const std::string& label, Person* person, FnSetInt fn)
{
// Do some stuff to identify an int within a message from the label.
// assume that 'val_i' contains the int value of the tag denoted by the
// label.
(person->*fn)(val_i);
}
Run Code Online (Sandbox Code Playgroud)
然后调用如下:
Person* person = new Person;
setMem("Name", person, Person::name ); // (1)
setMem("Age", person, Person::age ); // (2)
Run Code Online (Sandbox Code Playgroud)
这个想法似乎是传递一个标签,一个对象和一个适当的mutator的地址.第三个参数的类型用于让编译器选择要调用的重载,然后特定的重载就会获得一个合适的变量,并调用函数将其作为参数传递给对象设置值.
这适用于旧的Solaris编译器.但是,当它在GCC上编译时,我会在点上失败(1)并且(2):
error: no matching function for call to
'setMem( const std::string& label, Person* person, <unknown type> )'
Run Code Online (Sandbox Code Playgroud)
看起来新编译器将其Person::age视为一个类型而不是指向函数的指针,并且无法解决重载问题.我正在考虑更改代码以使用函数对象而不是直接指向函数.
我想知道调用代码是否可以保持这样的方式(即没有明确说明函数采用的类型),记住我不能更改Person类,并且理想情况下要将更改保持在最小.
首先更改声明:
typedef void (Person::*FnSetStr)(const std::string& s);
typedef void (Person::*FnSetInt)(const int& i);
Run Code Online (Sandbox Code Playgroud)
然后改变通话:
setMem("Name", person, &Person::name ); // (1)
setMem("Age", person, &Person::age ); // (2)
Run Code Online (Sandbox Code Playgroud)
在VS 2010中以警告级别4构建清洁.