c - 多个仅包含 header 的库导致重新定义错误

标签 c gcc nuklear

我正在使用名为 Nuklear 的仅 header 库.这是一个只有标题的库。使用来自不同文件的多个包含时遇到问题。它返回一个多定义示例:

...
obj/main.o:main.c:(.text+0x4a52b): multiple definition of `nk_sdl_font_stash_begin'
obj/components.o:components.c:(.text+0x4a56f): first defined here
obj/main.o:main.c:(.text+0x4a563): multiple definition of `nk_sdl_font_stash_end'
obj/components.o:components.c:(.text+0x4a5a7): first defined here
obj/main.o:main.c:(.text+0x4a5f4): multiple definition of `nk_sdl_handle_event'
obj/components.o:components.c:(.text+0x4a638): first defined here
obj/main.o:main.c:(.text+0x4ac9f): multiple definition of `nk_sdl_shutdown'
obj/components.o:components.c:(.text+0x4ace3): first defined here

我正在尝试将库包含到 2 个文件中。

ma​​in.c

#define SDL_MAIN_HANDLED
#include <GL/glew.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_opengl.h>

#define NK_INCLUDE_FIXED_TYPES
#define NK_INCLUDE_STANDARD_IO
#define NK_INCLUDE_STANDARD_VARARGS
#define NK_INCLUDE_DEFAULT_ALLOCATOR
#define NK_INCLUDE_VERTEX_BUFFER_OUTPUT
#define NK_INCLUDE_FONT_BAKING
#define NK_INCLUDE_DEFAULT_FONT
#define NK_IMPLEMENTATION
#define NK_SDL_GL3_IMPLEMENTATION
#include "nuklear.h"
#include "nuklear_sdl_gl3.h"
#include "components.h"
...

components.c

#define SDL_MAIN_HANDLED
#include <GL/glew.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_opengl.h>

#define NK_INCLUDE_FIXED_TYPES
#define NK_INCLUDE_STANDARD_IO
#define NK_INCLUDE_STANDARD_VARARGS
#define NK_INCLUDE_DEFAULT_ALLOCATOR
#define NK_INCLUDE_VERTEX_BUFFER_OUTPUT
#define NK_INCLUDE_FONT_BAKING
#define NK_INCLUDE_DEFAULT_FONT
#define NK_IMPLEMENTATION
#define NK_SDL_GL3_IMPLEMENTATION
#include "nuklear.h"
#include "nuklear_sdl_gl3.h"

Nuklear 库已经包含 header 保护,所以我不确定为什么会出现此错误。有什么建议吗?

最佳答案

来自 GitHub 上的自述文件:

This library is self contained in one single header file and can be used either in header only mode or in implementation mode. The header only mode is used by default when included and allows including this header in other headers and does not contain the actual implementation.

The implementation mode requires to define the preprocessor macro NK_IMPLEMENTATION in one .c/.cpp file before #includeing this file, e.g.:

#define NK_IMPLEMENTATION
#include "nuklear.h"

因此,main.ccomponents.c 中只有一个应该包含 #define NK_IMPLEMENTATION — 但您在两者中都定义了它。

修复

  • components.c 中删除 #define NK_IMPLEMENTATION
  • 不要包含除 nuklear.h 之外的任何其他 Nuklear header — 说明并没有告诉您这样做(至少,表面上没有;也许其他地方是这样说的,但是……)。

文档还指出:

IMPORTANT: Every time you include "nuklear.h" you have to define the same optional flags. This is very important not doing it either leads to compiler errors or even worse stack corruptions.

可能值得拥有自己的 header — 例如 use_nuklear.h,但我相信您会想到一个更好的名称 — 它包含正确的 NK_ * 选项(除 NK_IMPLEMENTATION 之外的所有选项)。然后在您的源文件中#include "use_nuklear.h"。这样一来,如果(当)您更改选项时,您只有一个地方可以更改 — 并且重建将是一致的。

关于c - 多个仅包含 header 的库导致重新定义错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56620492/

相关文章:

c - "gcc a.c -o a.c"我怎样才能恢复真正的.c文件

c++ - 为什么编译器错误地检测不到正确的函数签名?

c - nuklear 简单示例中未显示窗口

c - 在整数数组的情况下,指针减法究竟是如何工作的?

c - 代理中的非阻塞套接字和 poll() 怪癖

c - 在并行环境中使用 fork、exec 和管道时出现死锁

c++ - C/C++ select在linux下如何与gpio协同工作?

linux - 为什么我的代码在为性能分析 (-pg) 编译时,多线程运行速度比单线程运行速度慢?