2017-04-07 52 views
0

我有一些对象结构看起来像这样:访问子结构值

struct Object { 
    string type; 
    Color c; 
    float ambient, diffuse; 
}; 

struct Sphere: Object { 
    Point center; 
    float radius; 
}; 

struct Square: Object { 
    Point loc; 
    float len; 
}; 

而且我有一个充满球和广场结构向量:

vector<Object> objs; 
Sphere sp = //sphere stuff 
Square sq = //square stuff 
objs.push_back(sp); 
objs.push_back(sq); 

我可以访问父结构中的值就好了,但我很难弄清楚如何访问Sphere和Square结构中的值。这就是我现在正在做的:

cout << objs.at(i).type << endl; //This works 
cout << objs.at(i).center.x << endl; //Not working 

有谁知道如何做到这一点?

+1

首先[read about object slicing](http://stackoverflow.com/questions/274626/what-is-object-slicing)。然后学习更多关于*指针*的知识。最后关于[upcasting和(更具体地)*** downcasting ***](https://www.tutorialcup.com/cplusplus/upcasting-downcasting.htm)以及如何使用['dynamic_cast'](http:///en.cppreference.com/w/cpp/language/dynamic_cast)。那么你应该知道如何解决你的问题。 –

回答

1

你不能,他们不再存在。您不存储Square s或Sphere s在vector中,您只是存储Object s。您应该阅读What is object slicing?

这就是说,如果你不是存储指针Object S,std::vector<Object*>你可以通过指针指向派生类型的对象。但是,您如何知道vector中的哪个元素是Square,哪个元素是Sphere。有一个基类的全部目的是提供一种接口到你想要的功能,通过virtual功能,它在派生类以不同的方式实现

struct Base { 
    virtual void foo() { std::cout << "foo in base\n"; } 
}; 
struct Derived1 : Base { 
    void foo() override { std::cout << "foo in Derived1\n"; } 
}; 
struct Derived2 : Base { 
    void foo() override { std::cout << "foo in Derived2\n"; } 
}; 

Derived2 d; 
Base* b = &d; 
b->foo(); // prints "foo in Derived2\n" 

那说,如果你确定它是Squaredynamic_cast<Square*>(objP),如果你不确定(如果你错了,它将返回一个空指针),从Object*得到Square*,使用static_cast<Square*>(objP)虽然这样做可能表明设计不好!


此外,请重新考虑你的东西通常被认为是不好的做法使用:using namespace std;endl(这些链接指向的解释)。

+1

好点,谢谢!显然我避免了这么多,我忘了它是如何工作的。 – BoBTFish

+0

'dynamic_cast '会抛出错误,虽然:) – Quentin

+0

@Quentin我上面的评论是对(自从删除)的回应一些程序员专家指出,它返回null指针,抛出引用。我原本错误地说它会抛出。 – BoBTFish