一切都很好,最后一个问题很烦人。编译很棒,但是链接失败:

bash-3.2$ make
g++ -Wall -c -g Myworld.cc
g++ -Wall -g solvePlanningProblem.o Position.o AStarNode.o PRM.o PRMNode.o World.o SingleCircleWorld.o Myworld.o RECTANGLE.o CIRCLE.o -o solvePlanningProblem

**Undefined symbols:

"vtable for Obstacle", referenced from:
      Obstacle::Obstacle()in Myworld.o

"typeinfo for Obstacle", referenced from:
      typeinfo for RECTANGLEin RECTANGLE.o
      typeinfo for CIRCLEin CIRCLE.o

ld: symbol(s) not found

collect2: ld returned 1 exit status

make: *** [solvePlanningProblem] Error 1**

障碍物
#ifndef Obstacle_hh
#define Obstacle_hh

#include <vector>
#include <iostream>

class Obstacle{
public:
    Obstacle(){}
    virtual bool collidesWith(double x,double y);
    virtual void writeMatlabDisplayCode(std::ostream &fs);
    virtual ~Obstacle(){}
};
#endif

我有什么问题?我可以发布您需要分析的任何代码。

最佳答案

您声明了一个非抽象类Obstacle,但并未实现其所有成员函数。

最好将其声明为抽象类:

class Obstacle{
public:
    Obstacle(){} // this is superfluous, you can (and should) remove it
    virtual bool collidesWith(double x,double y) = 0;
    virtual void writeMatlabDisplayCode(std::ostream &fs) = 0;
    virtual ~Obstacle(){}
};

原因是您会在许多C++编译器中找到一种试探法-避免在定义了第一个非内联虚拟成员函数(如果有)的情况下不必要地为它们创建的类创建重复的vtable和typeinfo。

您的代码将破坏该方案:您将Obstacle.hh包含在某个编译单元中,编译器将具有Obstacle的类collidesWith视为第一个非内联虚拟成员函数,但当前编译单元中未定义该类,因此编译器认为可以推迟为该类创建vtable和typeinfo。由于没有collidesWith的定义,因此在链接程序时它们都最终丢失。

09-25 18:03