【问题标题】:Forward-declare struct which only has definition in a library cpp仅在库 cpp 中定义的前向声明结构
【发布时间】:2015-08-11 13:55:38
【问题描述】:

我正在使用子弹 3 物理库,它在其中一个 cpps 中有以下结构定义:

struct btSingleContactCallback : public btBroadphaseAabbCallback
{

    btCollisionObject* m_collisionObject;
    btCollisionWorld*   m_world;
    btCollisionWorld::ContactResultCallback&    m_resultCallback;


    btSingleContactCallback(btCollisionObject* collisionObject, btCollisionWorld* world,btCollisionWorld::ContactResultCallback& resultCallback)
        :m_collisionObject(collisionObject),
        m_world(world),
        m_resultCallback(resultCallback)
    {
    }

    virtual bool    process(const btBroadphaseProxy* proxy)
    {
        btCollisionObject*  collisionObject = (btCollisionObject*)proxy->m_clientObject;
        if (collisionObject == m_collisionObject)
            return true;

        //only perform raycast if filterMask matches
            if(m_resultCallback.needsCollision(collisionObject->getBroadphaseHandle())) 
        {
            btCollisionObjectWrapper ob0(0,m_collisionObject->getCollisionShape(),m_collisionObject,m_collisionObject->getWorldTransform(),-1,-1);
            btCollisionObjectWrapper ob1(0,collisionObject->getCollisionShape(),collisionObject,collisionObject->getWorldTransform(),-1,-1);

            btCollisionAlgorithm* algorithm = m_world->getDispatcher()->findAlgorithm(&ob0,&ob1);
            if (algorithm)
            {
                btBridgedManifoldResult contactPointResult(&ob0,&ob1, m_resultCallback);
                //discrete collision detection query

                algorithm->processCollision(&ob0,&ob1, m_world->getDispatchInfo(),&contactPointResult);

                algorithm->~btCollisionAlgorithm();
                m_world->getDispatcher()->freeCollisionAlgorithm(algorithm);
            }
        }
        return true;
    }
};

问题是,该结构从未在任何标题中声明,但是我需要能够创建这种类型的对象。子弹库是静态链接的,所以我想我应该可以在我的主程序中自己声明它:

struct btSingleContactCallback
    : public btBroadphaseAabbCallback
{
    btCollisionObject *m_collisionObject;
    btCollisionWorld *m_world;
    btCollisionWorld::ContactResultCallback &m_resultCallback;
    btSingleContactCallback(btCollisionObject *collisionObject,btCollisionWorld *world,btCollisionWorld::ContactResultCallback &resultCallback);
    virtual bool process(const btBroadphaseProxy *proxy);
};

这实际上工作正常,只要我在调试模式下编译。但是,当尝试在发布模式下编译时,我得到一个未解决的符号错误:

physenvironment.obj : error LNK2001: unresolved external symbol "public: __cdecl btSingleContactCallback::btSingleContactCallback(class btCollisionObject *,class btCollisionWorld *,struct btCollisionWorld::ContactResultCallback &)" (??0btSingleContactCallback@@QEAA@PEAVbtCollisionObject@@PEAVbtCollisionWorld@@AEAUContactResultCallback@2@@Z)

这可能与 c++ 的名称修改有关吗?有没有办法避免它,而不必开始对库本身进行修改?

【问题讨论】:

  • 为什么不把这个结构的实现复制到你的代码中呢?
  • 您能否详细说明您试图通过使用该库的私有实现细节来解决的问题?
  • 我支持 Mark B。你确定你应该实例化那个类吗?我的意思是,通常,库带有包含前向声明的标头。如果您真的应该使用该类,那么您应该通知库的作者,以便他们在标题中包含声明(但这会令人惊讶)。
  • 我认为这是库中的疏忽,但是有一个 public 函数将这种类型的结构作为参数之一,我需要的没有其他选择去做。

标签: c++ struct static-libraries forward-declaration unresolved-external


【解决方案1】:

从五分钟看库代码,您实际上应该使用公共的ContactResultCallback,让btCollisionWorld::contactTest 的实现为您创建和使用私有的btSingleContactCallback

【讨论】:

  • 是的,但是我需要访问 btBroadphaseInterface::aabbTest ,这也是一个公共函数,但只接受 btSingleContactCallback 类型的对象。 aabbTest 允许我指定一个形状,而 contactTest 没有。
  • 据我所知btBroadphaseInterface::aabbTest 接受btBroadphaseAabbCallback 回调。
  • btSingleContactCallback 派生自 btBroadphaseAabbCallback。我可以编写自己的从 btBroadphaseAabbCallback 派生的类,但是 btSingleContactCallback 已经完全符合我的要求,我想避免复制粘贴它。
【解决方案2】:

你没有实现构造函数。

【讨论】:

  • 不,构造函数已经在库中实现了。
  • 类也是如此,但你也不能使用它。链接器已确定您不能(因此不应该)在其翻译单元之外使用该函数,并且未在版本 .lib 中包含该符号
猜你喜欢
  • 2010-10-11
  • 2012-06-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多