引用了外部内联函数,但未定义
extern inline function was referenced but not defined
我有一个函数(我们称之为void foo(void) {}
),我希望它是内联的。但我在文件中定义了它.cpp。
我无法将函数移动到标题,因为它正在使用.cpp中的其他函数。
编辑:
下面的代码就像真正的代码一样,不使用C ++功能。我可以清楚地补充:
#ifdef __cplusplus
extern "C"
#endif
如果我想将下面的代码转换为 c99,我只需要更改我的项目属性(或 makefile,如果您愿意)而不是代码。我也在问 c++,因为它可以解决我的问题,而 c99 不能。
因此,我问题中的 C 和 C++ 标签是合理的。 代码是可移植
的 请参阅: 何时在C++中使用外部"C"?
编辑#2好的,
我知道我必须foo()
定义放在头文件中。如何在不将它们移动到头文件的情况下从foo()
调用func_a()
和func_b()
?有什么解决方法吗?
示例
文件.c/.cpp:
int func_a (int a, int b, int c) {/*...*/};
double func_b (double a, double b, double c) {/*...*/};
void foo (int a, double b) { // unction definition
//...
int myInt = func_a(a, 2, 3);
//...
double myDouble = func_b(1.5f, b, 3.5f);
//...
}
文件.h:
// Something before.
void foo (int a, double b); // function declaration
// Something after.
我想指出:
- 我正在使用Visual Studio 2015。
- 我正在写一个比较大的项目(~7000行代码)。它是物理系统的模拟。
file.h
包含在许多其他编译单元中。foo(int, double)
很小,它从file.cpp
调用其他函数- 由于优化原因,我想使
foo(int, double)
内联(我最终将使用__forceinline__
) - 我在我的程序中多次打电话给
foo()
。此外,它在几个while循环中使用(每个循环100k +迭代),因此让这个符号foo()
内联是很广阔的。 - 我厌倦了仅标题库。
我尝试:
file.c/.cpp:
extern inline
void foo (int a, double b) {*...*}; // Definition
文件.h:
extern inline
void foo (int a, double b); // Declaration
但我不断收到警告:
warning : extern inline function "foo" was referenced but not defined
我不明白为什么我会收到这个警告。
有没有办法:
- 在我的.cpp文件中保留
foo()
的定义?但仍然使其内联 - 将
foo()
移到file.h
,保持func_a()
和func_b()
在file.cpp
内,但使func_a()
符号和func_b()
符号对foo()
"可见"(而且只对foo()
!)从file.cpp
- 还有其他解决方法吗?
Sory 我还在学习 cpp,我不知道我的问题是否清楚,或者是否可以从.cpp文件中内联函数。
在C++中,inline
关键字的意思是:
- 的主体必须存在于使用该函数的每个源文件中。
- 所有源文件中函数的"主体"必须逐个令牌和逐个实体相同。
- 编译器和链接器必须确保它们对具有这些"多个主体"的函数感到满意
这就是它所做的一切。实际上,这意味着它启用并强制您将函数体放入头文件中。
关键字本身与函数内联本身无关。只是如果编译器希望能够内联函数的主体,那么在编译调用代码时必须有权访问它;换句话说,函数的主体必须位于同一源文件或该源文件包含的头文件中。
如果要使编译器能够在所有调用站点中内联函数,并且这些调用站点发生在多个源文件中,则必须将函数放入头文件中(并将其标记为inline
)。
另一方面,链接器也可以进行内联,称为链接时间代码生成或整个程序优化或类似的东西(取决于工具链的供应商)。启用此操作将
- 延长构建时间,以及
- 允许链接器跨源文件将函数内联到调用站点中
因此,要内联函数,您有两种选择。将函数放入头文件中,或者启用并依靠链接时间优化来为您内联它。
在您的特定情况下,要使用__forceinline__
,您将在头文件中定义foo
。这需要定义foo
才能看到func_a
和func_b
的声明。为了防止命名空间污染,您可以在foo
范围内声明这些函数:
inline void foo(int a, double b) { // function definition
int func_a(int, int, int);
double func_b(double, double, double);
//...
int myInt = func_a(a, 2, 3);
//...
double myDouble = func_b(1.5f, b, 3.5f);
//...
}
- 从python调用openMP共享库时,未定义opnMP函数
- 具有外部"c"和程序集的未定义函数
- 已定义函数时出现 G++ "未定义的引用"错误
- 对显式实例化的模板函数的未定义引用
- 编译问题:在函数"_start"中:未定义对"主"的引用 collect2:错误:ld 返回 1 个退出状态
- 为什么我会收到警告,指出函数已使用但未定义,以及已定义但未使用?
- 2个模板化类的非模板友元函数未定义引用错误
- 使用内联函数 c++ 的未定义引用
- MacOS 上的 Xcode 11 项目不在一个函数中使用 sin 和 cos:未定义的符号"___sincosf_stret"
- 仅在 MacOS 上析构函数的未定义符号
- 如果用户尝试从 JS 调用对象的未定义函数C++则回调C++代码
- C++编译并链接到指向未定义函数的指针
- C++:定义函数时出现未定义函数错误
- 奇怪的未定义函数引用,函数调用C++不存在
- 类型为"double"的输入参数的未定义函数
- Android NDK:创建一个未定义函数的库
- c++ Builder调用未定义函数hypot/ceil/floor/fab
- 通过 GDB 设置断点时未定义函数"d::~d"
- 如何像传递未定义函数一样传递未定义方法
- 确定未定义函数的参数类型