为啥我的讲师编写的所有 C 文件的第一行都以单个 # 开头?

Posted

技术标签:

【中文标题】为啥我的讲师编写的所有 C 文件的第一行都以单个 # 开头?【英文标题】:Why do all the C files written by my lecturer start with a single # on the first line?为什么我的讲师编写的所有 C 文件的第一行都以单个 # 开头? 【发布时间】:2018-01-19 14:46:45 【问题描述】:

我正在阅读一些 C 课程笔记,每个 C 程序源文件在程序的第一行都以单个 # 开头。

然后是空行,然后是 main 函数。

# 的原因是什么?

(现在已经过期了,我真的不能问小伙子。)

这是一个例子:

#

#include <stdio.h>
int main() 
   printf("Hello, World!");
   return 0;

【问题讨论】:

***.com/questions/35207515/… @Bathsheba 最后一个上的时间戳表明您在提出问题后仅一分钟就给出了相当详细的答案,并附有 C99 参考标准的相关引用。你绝对是个阴谋家。可能在光明会。这两个问题怎么会如此受欢迎? 对我来说,受欢迎程度有点奇怪。通过编辑,您确实有五分钟的宽限期来正确地进行编辑,并且到目前为止的编辑历史不会显示在历史中 - 只是五分钟的草稿和第一次尝试的时间。这个问题现在与另一个问题相关联的事实只会增加对这两个问题的投票。 【参考方案1】:

哇,这个要求可以追溯到 1970 年代

在预标准化 C 的非常早期的日子里,如果你想调用 预处理器,那么你必须写一个 # 作为第一件事源文件的第一行。 在文件顶部写入# 可以灵活地放置其他预处理器指令。

来自an original C draft by the great Dennis Ritchie himself:

12.编译器控制线

[...] 为了使 [the] 预处理器被调用,非常有必要 程序的第一行以#开头。由于预处理器忽略了空行,因此该行不需要包含其他 信息。

该文档非常适合阅读(让我可以像疯猫一样跳到这个问题上)。

我怀疑是讲师只是出于多愁善感——自 ANSI C 以来就没有必要这样做了。

【讨论】:

据我了解,要求不是第一个字符必须是一行上的#,只是它以#开头,所以为什么不直接#include?还是我理解错了? @Bathsheba "为了调用这个预处理器,程序的第一行必须以#开头。由于预处理器忽略了空行,所以这一行不需要包含其他信息。" 可以已经包含预处理器指令,但没有必要.... 当我开始用 C (1980) 编程时,这不是必需的。 ANSI C 直到 1989 年才标准化。 @federico-klez-culloca 如果它变成了一个包含,该文件可能会在没有前导 # 的情况下结束,因为将来有人会删除一个不需要的包含而没有意识到前导 # 的副作用。跨度> @Casanova - 不。这样做并接受这样的答案违反了网站规则。如果您明白我的意思,即使没有相互投票,在不同帐户下提问和回答也违反了网站规则的精神。尽管使用同一个帐户回答您自己的问题并接受该答案并没有什么害处 - 我过去曾这样做过。【参考方案2】:

什么都不做

按照 C/C++ 的 ISO 标准:

表单的预处理指令

# new-line

没有效果。

因此,在今天的编译器中,空哈希没有任何作用(比如-new-line ; 没有任何功能)。


PS:在 * 预标准化的 C* 中,# new-line 具有重要作用,它用于调用 C 预处理器(正如 @Bathsheba 所指出的)。所以,这里的代码要么是在那个时间段内写的,要么是程序员的习惯。


编辑:最近我遇到了这样的代码-

#ifdef android
#
#define DEVICE_TAG "ANDROID"
#define DEBUG_ENABLED
#
#else
#
#define DEVICE_TAG "NOT_ANDROID"
#
#endif /* ANDROID */

在这里,那些空的哈希值只是为了让代码看起来更好。它还通过指示它是一个预处理器块来提高可读性。

【讨论】:

【参考方案3】:

你需要了解 C 的编译过程。因为那是“必须知道”如何将源代码转换为可执行二进制代码(文件)的过程。

在编译过程中,C 源代码必须经过预处理器部分。但是如何告诉Compiler对代码进行预处理呢?...那个时候#Symbol被引入到Preprocess到编译器的指标中了。

例如#define PI 3.141 在源代码中。然后它将在预处理会话之后发生变化。也就是说,所有的 PI 都会变成 3.141。

这就像#include &lt;stdio.h&gt;,标准的I/O函数将被添加到你的源代码中。

如果你有一台 Linux 机器,像 gcc -save-temps source_code.c 这样编译。并查看编译器输出。

【讨论】:

问题不在于# 作为前缀。它在问你为什么要在每个文件的顶部放置一个 #

以上是关于为啥我的讲师编写的所有 C 文件的第一行都以单个 # 开头?的主要内容,如果未能解决你的问题,请参考以下文章

Linux脚本练习之script003-将 `/etc/passwd` 文件的第一列取出,并且每列都以一行字符串 `“The account is ‘root‘“` 显示。

老男孩教育每日一题-第65天-编写脚本,取出/tmp目录下面的所有文件的第一行

如何将文本文件的第一行放在结束位置

为啥 Java 会忽略 .properties 文件的第一行?

为啥n个线程的平均速度不如C中的单个线程快?

Python 没有接收到来自 Arduino Mega 2560 的第一行串行数据,而是接收到所有后续数据,为啥会发生这种情况?