例如,当我们编译以下代码时:
printf("hello);
我们收到警告,然后发现有关丢失的"
字符的错误。在我看来,警告告诉我们一个可以编译的代码,但其行为可能与开发人员期望的不同。因此,我的理解错过了两件事:
编辑(我正在尽力处理偏离主题的投票建议):
1.所需行为:只有一条错误诊断消息,不需要对同一事件发出警告。
2.1 printf_s()是否有同样的问题?我试图启用-c11选项但没有成功。
2.2发出警告的历史原因在我看来似乎并不合理,因为在类似的情况下为什么没有使用这种双重信息(在新的c版本中禁止使用旧的结构)。
答案 0 :(得分:4)
在我看来,警告告诉我们可以编译的代码 但是他的行为可能与开发者的行为有所不同 预计。因此,我的理解错过了两件事:
您的意见与此无关,C标准和C ++标准都不区分不同类别的诊断消息。事实上,许多编制者确实区分了一种基于历史的惯例,尽管这是一种广泛观察到的惯例。最重要的是你的编译器通过这种区分意味着什么(如果它确实是一个)。另一方面,幸运的是,GCC确实采用了与您描述的类似的约定,如记录in its manual:
错误报告无法编译程序的问题。 [...]。
警告报告代码中可能表示存在问题的其他异常情况,尽管编译可以(并且确实)继续进行。 [...]
(GCC 7.2手册,第13.9节;相同或类似的文本也出现在手册的早期版本中,至少回到第4节。)
请注意,文档对警告的含义略有不同:GCC警告表示编译可以继续,但无法保证它可以成功完成。如果确实最终不能,那么我希望GCC根据其文档也发布错误诊断。这正是我在这个测试程序中观察到的,无论是编译为C还是C ++:
#include <stdio.h>
int main(void) {
printf("hello);
}
我真的认为你在远过多的事实是GCC除了在这种情况下发生错误之外还会发出警告。这是一个没有特别重要意义的实施怪癖。
- 是否有完整的代码可以在包含这样一部分代码时编译而没有错误。
醇>
这完全取决于你的意思。琐碎的是,我可以在上面的程序中用//
作为错误行的前缀,将它变成注释,这将使它成为完全有效的C和C ++源代码。我可以添加到给定源的多种其他方式,而不删除任何使其有效的方法 - 其中一些甚至会产生一个实际执行printf()
调用的程序。
我想你真正想知道的是,是否有代码可以引起GCC的警告而不是相应的错误。据我所知,现代GCC不提供这样的代码,但historically, GCC did allow it作为扩展,以字符串文字中嵌入的,未转义的换行符的形式出现:
printf("hello);
Goodbye");
该行为已在GCC 3.2中弃用,并且早在GCC 4(当前为7.2)时就被删除了。
- 如果这样的代码不存在,为什么这个缺失的字符情况不会给我们一个错误(不是警告+错误)。
醇>
我们只能猜测,但它似乎可能源于上述语言扩展的历史存在。而且,你做的太多了。 GCC针对同一问题发出了两个诊断信息 - 那又怎么样?诊断的最终目的是帮助您弄清楚代码的错误或错误,GCC在这种情况下发出的诊断就可以完成这项工作。
答案 1 :(得分:1)
您的编译器在检测到程序格式错误时可能会发出错误,并描述程序在其发生位置无法正常形成的直接原因。
这通常是无用的,因为这个错误可能已经走了很多行。
它还会发出猜测(通常是有根据的猜测)实际导致问题的警告。也许您忘记了前一行的;
,未能关闭{
或(
。警告不是&#34;这个标记是错误点#34;而是#34;这是一切都出错的地方&#34;。
实际上,C ++标准本身并不区分警告和错误;他们都是诊断。它要求某些事情导致诊断,并且不禁止编译器发出其他诊断信息。编译器甚至可以通过警告自由编译生成错误的程序。
我希望&#34;字符串&#34;中的换行符出错,然后是指向公开引用的警告。