我对 Ubuntu 还很陌生,最近我在终端中输入以下命令创建了一个 .o 文件:
g++ -Wall -std=c++11 -c average.cpp -o average.o
但是,当我尝试执行 .o 文件时,出现此错误:
bash: ./average: No such file or directory
尽管我显然有这个文件。所以我决定输入file average.o
,结果得到了这个:ELF 64-bit LSB relocatable, x86-64, version 1 (SYSV), not stripped
。
问题是否在于它必须是 32 位可执行文件?如果是这样,我该如何将其更改为 32 位可执行文件?
编辑:所以我能够创建average
,但是当我尝试运行它时,我会收到此错误:
terminate called after throwing an instance of 'std::logic_error'
what(): basic_string::_M_construct null not valid
Aborted (core dumped)
编辑 2:我能够修复核心转储并设法授予我的文件运行的权限,但现在,我收到一个新错误:
bash: ./average: cannot execute binary file: Exec format error
。
当我这样做时file averge
,我得到了这个:
average: ELF 64-bit LSB relocatable, x86-64, version 1 (SYSV), not stripped
。
答案1
.o
文件不是可执行文件。
请尝试以下操作之一:
跳过文件创建
.o
和可执行文件的创建g++ -Wall -std=c++11 average.cpp -o average ./average
将
.o
文件链接到可执行文件g++ -Wall -std=c++11 -c average.cpp -o average.o g++ -Wall -std=c++11 -o average average.o ./average
如果average
文件仍然无法运行,请尝试授予其权限
chmod +x average
编辑(2017 年 7 月 3 日)
解释
我被要求解释这些命令的作用,所以就这样。
克++
这是编译器,它将解释您的代码并将其转换为您的机器可以解释的机器代码。
您可以在手册页上阅读更多相关信息。只需打开终端并输入man g++
。
-墙
此标志告诉编译器通知您几乎所有警告(Wall = Warn all)。请查看下面的代码。
int i = 1;
if (i > i) { ... }
如果您不放置标志,-Wall
则不会显示任何警告,但如果您放置了标志,则会看到类似以下内容:
warning: self-comparison always evaluates to false [-Wtautological-compare]
if (i > i) {}
-std=c++11
使用此标志,您可以告诉编译器要使用哪个版本的语言。这是一个相当复杂的话题,但简而言之,C++ 是一种活生生的语言,这意味着它会随着时间而改变和改进,C++11 就是其中之一,它增加了很多改进。现在您可以使用-std=c++14
,今年某个时候您将能够使用-std=c++17
。
你似乎是 C++ 的新手,所以不用担心这个版本的所有问题!:D
-C
无需链接即可编译。
基本上允许创建.o
包含一堆数据,主要是编译后的代码和信息,以便编译器链接对象。
它使大型项目的编译更快,因为当您更改一个文件时,它只需要创建一个目标文件并将其与已编译的目标文件链接起来。
-o文件
摘自页面man
:
将输出放在文件中。这适用于生成的任何类型的输出,无论是可执行文件、目标文件、汇编文件还是预处理的 C 代码。
基本上,这个标志告诉编译器将它正在执行的任何过程(编译/链接/……)的结果放在哪里。
希望这个解释有帮助!:)
答案2
您应该检查文件权限,并确保权限设置为允许文件作为程序执行,同时在尝试执行文件时,您需要加上 .o 扩展名,因为根据经验,这是我能够从命令行执行文件的唯一方法
答案3
g++ -Wall -std=c++11 -c average.cpp -o average.o
将创建average.o
文件而不是average
,这就是为什么你会得到no such file
错误
首先创建average
文件然后尝试执行它。
尝试这个:
g++ -Wall -std=c++11 average.cpp -o average
然后给予许可:
chmod +x average
然后执行它
./average