一个类返回'int',其他返回'double'。在两个类的接口中,方法'GiveMeTheValue'的签名是什么。 我想编译以下代码:
class Interface
{
public:
virtual arbitrary_type GimeMeTheValue(void) {};
};
class TakeInt : public Interface
{
public:
arbitrary_type GimeMeTheValue(void) {
return 10;
}
};
class TakeDouble : public Interface
{
public:
arbitrary_type GimeMeTheValue(void) {
return 3.14;
}
};
int main()
{
Interface * obj;
obj = new TakeInt();
cout << obj -> GimeMeTheValue() << endl; // It's 10, thank you
obj = new TakeDouble();
cout << obj -> GimeMeTheValue() << endl; // Oh it's 3.14, I love you c++
}
当然没有这样的“arbitary_type”。 这有效......
class Interface
{
public:
virtual void * GimeMeTheValue(void) {};
};
class TakeInt : public Interface
{
public:
void * GimeMeTheValue(void) {
int value = 10;
int * ptr = &value;
return ptr;
}
};
class TakeDouble : public Interface
{
public:
void * GimeMeTheValue(void) {
double value = 3.14;
double * ptr = &value;
return ptr;
}
};
int main()
{
Interface * obj;
obj = new TakeInt();
cout << *( (int *) (obj -> GimeMeTheValue()) ) << endl;
obj = new TakeDouble();
cout << *( (double *) (obj -> GimeMeTheValue()) ) << endl;
}
处理“void *”相当复杂。有没有其他想法来实现简单的东西(比如在第一个代码示例中)?谢谢。
答案 0 :(得分:1)
基类Interface
无法知道每个后代想要返回的不同数据类型。使用不同的返回类型会破坏多态性的目的。因此,我认为这样做的唯一方法是让GiveMeTheValue()
返回一个对象类型,该对象类型知道它拥有什么样的值,然后使该对象可以流化。
enum VariantType {varNull, varInt, varDouble};
struct Variant
{
VariantType Type;
union {
int intValue;
double dblValue;
};
Variant() : Type(varNull) {}
Variant(int value) : Type(varInt), intValue(value) {}
Variant(double value) : Type(varDouble), dblValue(value) {}
void writeTo(std::ostream &strm)
{
switch (Type)
{
case varNull: strm << "(null)"; break;
case varInt: strm << intValue; break;
case varDouble: strm << dblValue; break;
}
}
};
class Interface
{
public:
virtual ~Interface() {}
virtual Variant GimeMeTheValue(void) = 0;
};
class TakeInt : public Interface
{
public:
Variant GimeMeTheValue(void)
{
return Variant(10);
}
};
class TakeDouble : public Interface
{
public:
Variant GimeMeTheValue(void)
{
return Variant(3.14);
}
};
std::ostream& operator<<(std::ostream &strm, const Variant &v)
{
v.writeTo(strm);
return strm;
}
int main()
{
Interface * obj;
obj = new TakeInt();
cout << obj->GimeMeTheValue() << endl; // It's 10, thank you
delete obj;
obj = new TakeDouble();
cout << obj->GimeMeTheValue() << endl; // Oh it's 3.14, I love you c++
delete obj;
}