为什么我的变量标记为 'extern' 时会出现 "undefined reference" 错误?链接器问题?
Why do I get "undefined reference"-error with a variable marked as 'extern'? Linker problem?
我知道这个问题已经被问过好几次(以类似的方式),但我不认为它是重复的,因为我的代码已经实现了提供给其他提问者的解决方案。如果我忽略了什么,我的问题当然可能会被标记为重复和降级。
我不得不使用外部变量,因为根据任务,我不能将它作为参数传递。问题:如果我想编译代码,则会抛出 "undefined reference"-错误。
代码:
header.h
#ifndef TEST_HEADER_H
#define TEST_HEADER_H
extern int var;
void increment();
#endif //TEST_HEADER_H
source1.c
#include <stdio.h>
#include "header.h"
int main ()
{
int var = 1;
printf("1) %d\n", var);
increment();
printf("2) %d\n", var);
return 0;
}
source2.c
#include "header.h"
void increment()
{
var++;
}
编译错误:
====================[ Build | test | Debug ]====================================
/root/clion-2019.1/bin/cmake/linux/bin/cmake --build /root/CLionProjects/test/cmake-build-debug --target test -- -j 2
Scanning dependencies of target test
[ 33%] Building C object CMakeFiles/test.dir/source1.c.o
[ 66%] Building C object CMakeFiles/test.dir/source2.c.o
[100%] Linking C executable test
/usr/bin/ld: CMakeFiles/test.dir/source2.c.o: in function `increment':
/root/CLionProjects/test/source2.c:5: undefined reference to `var'
/usr/bin/ld: /root/CLionProjects/test/source2.c:5: undefined reference to `var'
collect2: error: ld returned 1 exit status
make[3]: *** [CMakeFiles/test.dir/build.make:100: test] Fehler 1
make[2]: *** [CMakeFiles/Makefile2:73: CMakeFiles/test.dir/all] Fehler 2
make[1]: *** [CMakeFiles/Makefile2:85: CMakeFiles/test.dir/rule] Fehler 2
make: *** [Makefile:118: test] Fehler 2
CMakeLists.txt:
cmake_minimum_required(VERSION 3.14)
project(test C)
set(CMAKE_C_STANDARD 11)
add_executable(test source1.c header.h source2.c)
我还尝试将以下内容添加到 CMakeLists.txt,因为它在 "undefined reference"-错误的另一种情况下有所帮助,但在这种情况下没有任何区别。
find_library(LIBRT rt)
if(LIBRT)
target_link_libraries(test ${LIBRT})
endif()
我认为问题不在代码中,是吗?我认为这是在链接过程中。有人可以帮忙吗?提前致谢!
编辑:
它正在运行。我的问题不是我无法区分声明和定义,正如某些人假设的那样,而是我将 'source1.c' 中的定义设置在 'main'(本地)而不是外部(全局)的错误位置).所以,准确地说,我的误解是对外部声明与其定义之间范围的估计,如果你明白我的意思的话。诚然,这不是天才之举。 ;-) 谢谢您的帮助!
你误解了extern
的意思。
将变量(或函数)标记为 extern
不会 定义(创建)该变量。相反,它只是 声明 它存在于某处。您在任何地方都没有 var
的定义。
在您的 main
中您有 int var = 1;
但该定义是 local 到 main
。它不是全局的,任何其他功能都无法访问。
您应该将该变量定义移出 main
:
#include <stdio.h>
#include "header.h"
int var = 1;
int main ()
{
printf("1) %d\n", var);
increment();
printf("2) %d\n", var);
return 0;
}
相关说明:您应该避免使用全局变量。它们导致代码难以理解、调试和维护。
这个
extern int var; /* declaration, it doesn't exist until its not defined somewhere */
只是一个声明,你需要定义它。由于您没有为 var
提供 定义 ,链接器无法找到它,因此出现错误
undefined reference to `var'
请注意 source1.c
int var = 1;
它不是 extern
变量的定义,它是一个本地创建的具有功能范围的变量。
我知道这个问题已经被问过好几次(以类似的方式),但我不认为它是重复的,因为我的代码已经实现了提供给其他提问者的解决方案。如果我忽略了什么,我的问题当然可能会被标记为重复和降级。
我不得不使用外部变量,因为根据任务,我不能将它作为参数传递。问题:如果我想编译代码,则会抛出 "undefined reference"-错误。
代码:
header.h
#ifndef TEST_HEADER_H
#define TEST_HEADER_H
extern int var;
void increment();
#endif //TEST_HEADER_H
source1.c
#include <stdio.h>
#include "header.h"
int main ()
{
int var = 1;
printf("1) %d\n", var);
increment();
printf("2) %d\n", var);
return 0;
}
source2.c
#include "header.h"
void increment()
{
var++;
}
编译错误:
====================[ Build | test | Debug ]====================================
/root/clion-2019.1/bin/cmake/linux/bin/cmake --build /root/CLionProjects/test/cmake-build-debug --target test -- -j 2
Scanning dependencies of target test
[ 33%] Building C object CMakeFiles/test.dir/source1.c.o
[ 66%] Building C object CMakeFiles/test.dir/source2.c.o
[100%] Linking C executable test
/usr/bin/ld: CMakeFiles/test.dir/source2.c.o: in function `increment':
/root/CLionProjects/test/source2.c:5: undefined reference to `var'
/usr/bin/ld: /root/CLionProjects/test/source2.c:5: undefined reference to `var'
collect2: error: ld returned 1 exit status
make[3]: *** [CMakeFiles/test.dir/build.make:100: test] Fehler 1
make[2]: *** [CMakeFiles/Makefile2:73: CMakeFiles/test.dir/all] Fehler 2
make[1]: *** [CMakeFiles/Makefile2:85: CMakeFiles/test.dir/rule] Fehler 2
make: *** [Makefile:118: test] Fehler 2
CMakeLists.txt:
cmake_minimum_required(VERSION 3.14)
project(test C)
set(CMAKE_C_STANDARD 11)
add_executable(test source1.c header.h source2.c)
我还尝试将以下内容添加到 CMakeLists.txt,因为它在 "undefined reference"-错误的另一种情况下有所帮助,但在这种情况下没有任何区别。
find_library(LIBRT rt)
if(LIBRT)
target_link_libraries(test ${LIBRT})
endif()
我认为问题不在代码中,是吗?我认为这是在链接过程中。有人可以帮忙吗?提前致谢!
编辑:
它正在运行。我的问题不是我无法区分声明和定义,正如某些人假设的那样,而是我将 'source1.c' 中的定义设置在 'main'(本地)而不是外部(全局)的错误位置).所以,准确地说,我的误解是对外部声明与其定义之间范围的估计,如果你明白我的意思的话。诚然,这不是天才之举。 ;-) 谢谢您的帮助!
你误解了extern
的意思。
将变量(或函数)标记为 extern
不会 定义(创建)该变量。相反,它只是 声明 它存在于某处。您在任何地方都没有 var
的定义。
在您的 main
中您有 int var = 1;
但该定义是 local 到 main
。它不是全局的,任何其他功能都无法访问。
您应该将该变量定义移出 main
:
#include <stdio.h>
#include "header.h"
int var = 1;
int main ()
{
printf("1) %d\n", var);
increment();
printf("2) %d\n", var);
return 0;
}
相关说明:您应该避免使用全局变量。它们导致代码难以理解、调试和维护。
这个
extern int var; /* declaration, it doesn't exist until its not defined somewhere */
只是一个声明,你需要定义它。由于您没有为 var
提供 定义 ,链接器无法找到它,因此出现错误
undefined reference to `var'
请注意 source1.c
int var = 1;
它不是 extern
变量的定义,它是一个本地创建的具有功能范围的变量。