C 宏的作用域规则 [英] Scope rules for C macros

查看:7
本文介绍了C 宏的作用域规则的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我不是一个 C 程序员,但我假设 C 宏几乎是一种查找和替换功能,预处理器获取宏定义并将其放在看到宏名称的任何位置.

I'm not much of a C programmer, but I was under the assumption that C macros were almost sort of a find and replace feature where the pre-processor takes the macro definition and puts it wherever it sees the macro name.

这是 Dragon Book 的动态范围规则示例以及它们如何应用于宏:

This is the Dragon Book's example of dynamic scope rules and how they apply to macros:

#define a (x + 1)

int x = 2;
void b () { int x = 1; printf("%d
", a); }
void c () { printf("%d
", a); }
void main () { b(); c(); }

他们还讨论了动态范围规则如何应用于宏 a 中的名称 x.我的假设是它基本上会用 (x + 1) 替换 a 然后编译程序,因此范围规则与你有写成 (x + 1) 而不是 a (这将是静态范围规则).

They also discuss how dynamic scope rules apply to the name x within macro a. I was under the assumption that it would basically replace a with (x + 1) and then compile the program and so the scope rules would be exactly the same as if you had written (x + 1) instead of a (which would be static scope rules).

谁能澄清一下?

参考的书是编译器:原理、技术和工具第二版.引用的示例来自第 31-32 页.

Book referred to is Compilers: Principles, Techniques & Tools Second Edition. The example quoted is from pages 31-32.

推荐答案

你对#define行为的理解是正确的.

Your understanding of the #define behaviour is correct.

我认为这本书所说的动态范围"是指名称 x 是根据调用宏的环境而不是定义的环境来解析的.因此,如果您在#define 之前设置了一个全局变量 x=3,这与 #define 中 x 的值无关 - 无论您在哪里使用宏,它都会使用 x 的值 - 如果有其他一些本地使用宏的函数中的变量 x,则将使用本地值.

What I think the book means when it says "dynamic scoping" is that the name x is resolved based on the environment where the macro is called, not where it is defined. So if you've set a global variable x=3 just before your #define, that's irrelevant to the value of x in the #define - it will just use the value of x wherever you use the macro - if there is some other local variable x in the function where you use the macro, then the local value will be used.

这与词法范围(C 语言和几乎所有现代语言中实际使用的)形成对比,其中名称指的是其本地词法环境.例如,如果您将示例中的 #define 替换为简单语句 a = x+1,则函数中 a 的值将比 x 在该点发生的任何值大一其中 a = x+1 出现在代码中.如果在您使用值 a 的位置碰巧存在其他名为 x 的局部变量,则无关紧要.同样,如果你定义了一个函数 int f() { return x + 1;},x 将引用全局变量 x,而不是其他一些名为 x 的局部变量,它恰好存在于调用 f() 的位置.如果这看起来很明显,那是因为,正如我所说,几乎所有语言都使用词法范围(尽管 Perl,例如,也允许使用 local 函数的动态范围).

This is in contrast to lexical scoping (which is what is actually used in the C language, and in almost all modern languages), in which a name refers to its local lexical environment. For example, if you replaced the #define in your example by the simple statement a = x+1, then the value of a in the function would be one more than whatever x happened to be at the point where a = x+1 appears in the code. It wouldn't matter if some other local variable named x happened to exist at the point where you use the value a. Similarly, if you defined a function int f() { return x + 1; }, x would refer to the global variable x, not some other local variable named x that happens to exist where f() is called. If this seems blindingly obvious, it's because, as I said, pretty much all languages use lexical scope (although Perl, for example, also allows dynamic scope using the local function).

参见 http://en.wikipedia.org/wiki/Scope_(computer_science)#Lexical_scoping_and_dynamic_scoping 对这个概念进行更多解释.

See http://en.wikipedia.org/wiki/Scope_(computer_science)#Lexical_scoping_and_dynamic_scoping for a bit more of an explanation of the concept.

这篇关于C 宏的作用域规则的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆