从c++库外部访问静态时出现问题

Issue with accessing static from outside c++ library

本文关键字:问题 静态 访问 c++ 外部      更新时间:2023-10-16

我正在做一个项目,在这个项目中我有以下。。。

项目1

JNIBox2DWorld.h

static b2World* world = NULL;

JNIBox2DWorld.cpp

world = new b2World(gravity);

现在这似乎很好用,但我想添加一个OpenGL渲染器,所以我创建了一个新项目,并引用了旧的头文件。。。。

项目2

b2GLPolygonShape.h

#include <Box2D/JNIBox2DWorld.h>
...
class b2GLPolygonShape 
{
  public:
    void Draw();
    void Draw(b2PolygonShape* s);
};

b2GLPolygonShape.cpp

#include "b2GLPolygonShape.h"
void b2GLPolygonShape::Draw(){
LOGD("in Draw");
if(world == NULL){
    LOGD("World is not set for some reason");
}
else{
    LOGD("World is set");
}
}

我看到这个世界在Box2D库中工作,但当我试图通过我的新代码访问它时,它是空的。。。。

D/Native(14119):绘制

D/Native(14119):由于某种原因未设置World

为什么当我从我的新库调用它时,它显示为null,但从旧库调用它很好?既然它是静态的,它不应该同时工作吗?

我想您可能对static的作用有点困惑。当您在编译单元(通常是cpp文件)中声明全局静态变量时,这意味着该变量是编译单元的本地,并且在其他地方看不到

由于您在头文件中声明了一个全局静态变量,该头文件包含在两个独立的cpp文件中,因此这最终会导致两个非常不同的(编译单元本地)全局变量world。但是,在b2GLPolygonShape.cpp中创建的world变量与在JNIBox2DWorld.cpp中创建的变量无关。

您可能想要做的是在头文件中声明一个外部变量:

示例.h

extern b2World* world;

并且在一个(但只有一个)cpp文件中创建对象:

示例.cpp

b2World* world = new b2World(gravity);

在另一个cpp文件中,您可以使用对象:

test.cpp

#include <example.h>
void foo() {
  world->whatever();
} 

并且至少链接器应该是可以的。

然而,以这种方式使用全局变量会带来各种各样的麻烦(例如,初始化的顺序,仅举最明显的例子),因此您通常应该注意其他方式来实现你想要的。您已收到警告。祝你好运:-)