通过指向所述类的抽象父级的指针执行类的成员函数

时间:2010-07-20 00:57:26

标签: c++ pointers abstract-class access-violation

我创建了一个抽象基类Animal,它具有公共虚拟抽象方法makeSound()。我创建了一个子类Cow,它实现了Animal.makeSound()正如你所期望的那样(你知道......“moo”)。我有一个Farm类,它包含一个私有成员变量std::vector<Animal*> animals。在其中一种Farm方法中,我迭代所有动物并让它们发出声音。

for(unsigned int i = 0; i < animals.size(); i++)
{
   animals[i]->makeSound()
}

不幸的是我收到错误

  

0x65766974处的未处理异常   TestBed.exe:0xC0000005:Access   违规阅读地点0x65766974。

知道这里发生了什么吗?


更新:为每个请求添加更多代码

class Farm
{
public:
    Farm();
    virtual ~Farm(void);

    void setBarnOnFire();

private:
    vector<Animal*> animals;
};


Farm::Farm()
{
    animals.push_back(new Dog());
    animals.push_back(new Cat());
    animals.push_back(new Chicken());
    animals.push_back(new Horse());
    animals.push_back(new Cow());
}



Farm::setBarnOnFire()
{
    for(unsigned int i = 0; i < animals.size(); i++)
    {
       animals[i]->makeSound()
    }
}

我应该做些什么来初始化animals

解决方案:

所以你们都是正确的。我正在访问我不拥有的内存。但是我花了很长时间才追查它。这是由于对对象初始化如何发生的误解。基本上,为了“初始化”成员变量,我实际上是用局部变量覆盖它。然后我把当地人交给了我创造的所有动物。之后,动物会试图调用局部变量 - 它已不复存在。

1 个答案:

答案 0 :(得分:0)

好吧,让我猜一下:

“TestBed.exe中0x65766974处的未处理异常:0xC0000005:访问冲突读取位置0x65766974。”

似乎代码指针被发送到0x65766974(“异常在0x65766974”),但这不是一个有效的读取位置,更不用说代码:(“访问冲突读取位置0x65766974”,注意,相同的数字)

那么vtable或vtable指针是否可能被破坏? 也许对象被字符串覆盖?因为它存储在一个向量中,也许你在向量中的前一个对象中有一些溢出缓冲区(可能是一个char数组?),这会破坏下一个对象vtable指针?