2011-12-16 31 views
0

这里很难解释我想要做什么,但我有一个基类和两个继承此基类的类。两个继承它的类都有自己独特的成员。我希望能够将两者都传递给方法,并让该方法检测它是哪一个,然后访问它们的唯一成员。我不能认为只会有两个继承它的类,所以我正在寻找更通用的解决方案。如何将类传递给方法,并从基类中检测继承者?

这里是想我做的一个例子:

#include <iostream> 

class Base { 

    public: 
    int _type; 
    Base() { } 
}; 

class First : public Base { 
    public: 
    int _first_only; 

    First() { } 
}; 

class Second : public Base { 
    public: 
    int _second_only; 

    Second() { } 
}; 

void test (Base b) { 

    std::cout << "Type: " << b._type << std::endl; 

    if(b._type==1) { 
    std::cout << "First\n"; 
    // Want to be able to do this 
    std::cout << "Val: " << (First)b._first_only << std::endl; 
    } else if(b._type==2) { 
    std::cout << "Second\n"; 
    // And this 
    std::cout << "Val: " << (Second)b._second_only << std::endl; 
    } 
} 

int main() { 

    First f; 
    f._first_only=1; 
    f._type=1; 
    Second s; 
    s._type=2; 
    s._second_only=2; 

    test(f); 
    test(s); 
} 

回答

1

这类似于其他答案:

  1. 你可以写多态类使用虚函数来得到这个行为。
  2. 通过指针或引用传递Dervied类对象以获取多态行为。否则它会导致对象切片。您的test()函数会导致对象切片。

此代码也可能对您有所帮助。你可以看到有不同的方式来打印类型。我使用GetBaseType(),GetDerivedType()和GetType()。这些GetType()方法对你来说很方便。有两个方便的构造函数。构造函数允许初始化数据成员。

class Base { 
private: 
    int _type; 
public: 
    Base(int type) : _type(type) { } 
    int GetBaseType() { return _type; } 
    virtual int GetDerivedType() = 0; 
    virtual int GetType() { return _type; } 
}; 

class First : public Base { 
private: 
    int _first_only; 
public: 
    First() : Base(1), _first_only(1) { } 
    First(int first_only) : Base(first_only), _first_only(first_only) { } 
    int GetDerivedType() { return _first_only; } 
    virtual int GetType() { return _first_only; } 
}; 

class Second : public Base { 
private: 
    int _second_only; 
public: 
    Second() : Base(2), _second_only(2) { } 
    Second(int second_only) : Base(second_only), _second_only(second_only) { } 
    int GetDerivedType() { return _second_only; } 
    virtual int GetType() { return _second_only; } 
}; 

void test (Base &b) { 
    std::cout << "Type: " << b.GetBaseType() << std::endl; 
    std::cout << "Type: " << b.Base::GetType() << std::endl; 

    std::cout << "Dervied type: \n"; 
    std::cout << "Val: " << b.GetDerivedType() << std::endl; 
    std::cout << "Val: " << b.GetType() << std::endl; 
} 

int main() { 

    First f(1); 
    Second s(2); 

    test(f); 
    test(s); 

    First f1; 
    Second s1; 

    test(f1); 
    test(s1); 
} 
1
  1. 无论是在Base
  2. 声明virtual功能从FirstSecond移动对普通会员类型分为Base

为了您的具体问题,第二个选项是更好:

class Base { 
    public: 
    int _member; // have getter() method, if '_member' is private 
    Base() { } 
}; 

内,test()

void test (Base &b) { // <--- practice to pass by reference if copy is not needed 
    // use b._member; 
}; 
1

您的代码不会多态工作,因为你是通过传递函数参数值,这会导致切片。

如果你有一个方法对不同的类型做不同的事情,可以考虑为每种类型重载它。

0

三件事我会做:在类型代码

  • 一般切换没有考虑好面向对象的设计:除了拉切换到代码的类。
  • 我也会在特定类的构造函数中设置类型标签。
  • 正如其他人所提到的,您需要通过引用来传递参数以避免切片。

下面的代码是什么样子:

#include <iostream> 

class Base { 

    public: 
    int _type; 
    Base() { } 
    virtual void print_to_stream(std::ostream & os) const =0; 
}; 

class First : public Base { 
    public: 
    int _first_only; 

    First() { _type =1; } 
    void print_to_stream(std::ostream & os) const 
    { 
     os<<"First\n"; 
     os<<"Val: " << _first_only << std::endl; 
    } 
}; 

class Second : public Base { 
    public: 
    int _second_only; 

    Second() { _type=2; } 

    void print_to_stream(std::ostream & os) const 
    { 
     os << "Second\n"; 
     os << "Val: " << _second_only << std::endl; 
    } 
}; 

void test (Base & b) 
{ 
    std::cout << "Type: " << b._type << std::endl; 
    b.print_to_stream(std::cout); 
} 

int main() { 
    First f; 
    f._first_only=1; 
    Second s; 
    s._second_only=2; 

    test(f); 
    test(s); 
} 
相关问题