10

我一直在阅读很多关于为什么全局变量不好以及为什么不应该使用它们的文章。然而,大多数常用的编程语言都以某种方式支持全局变量。

所以我的问题是仍然需要全局变量的原因是什么,它们是否提供了一些无法替代实现的独特且不可替代的优势?与用户指定的自定义间接检索相比,全局寻址是否有任何好处以检索其本地范围之外的对象?

据我了解,在现代编程语言中,全局寻址带来的性能损失与计算内存地址的每个偏移量相同,无论它是从“全局”用户内存开头的偏移量还是从 athis或任何偏移量的偏移量其他指针。因此,在性能方面,用户可以使用公共指针间接在需要它们的狭义情况下伪造全局变量,而不会损失实际全局变量的性能。还有什么?全局变量真的需要吗?

4

6 回答 6

18

全局变量通常不是因为它们的性能而糟糕,它们之所以糟糕是因为在大型程序中,它们很难封装所有内容 - 存在信息“泄漏”,通常很难弄清楚发生了什么。

基本上你的变量的范围应该只是你的代码工作和相对容易理解所需要的,仅此而已。在打印出十二次表的程序中拥有全局变量是可以管理的,在数百万行的会计程序中拥有它们并不是那么好。

于 2013-08-31T11:42:01.787 回答
6

我认为这是另一个类似的主题goto- 这是一个“宗教事物”。

有很多方法可以“解决”全局变量,但是如果您仍然在代码的不同位置访问相同的内存位,您可能会遇到问题。

全局变量对某些事情很有用,但绝对应该“小心”使用(比 更重要goto,因为误用的范围更大)。

有两件事使全局变量成为问题: 1. 很难理解对变量做了什么。2. 在多线程环境中,如果从一个线程写入全局并由任何其他线程读取,则需要某种同步。

但有时全局变量非常有用。例如,拥有一个config变量来保存来自应用程序配置文件的所有配置值。另一种方法是将它存储在从一个函数传递到另一个函数的某个对象中,这只是额外的工作,没有任何好处。特别是如果配置变量是只读的。

然而,作为一个整体,我建议避免使用全局变量。

于 2013-08-31T11:49:55.073 回答
5

Global variables imply global state. This makes it impossible to store overlapping state that is local to a given part or function in your program.

For example, let stay we store the credentials of a given user in global variables which are used throughout our program. It will now be a lot more difficult to upgrade our program to allow multiple users at the same time. Had we just passed a user's state as a parameter, to our functions, we would have had a lot less problems upgrading to multiple users.

于 2013-08-31T14:15:07.373 回答
1

我的问题是仍然需要全局变量的原因是什么,

有时您需要从许多不同的功能访问相同的数据。这是你需要全局变量的时候。

例如,我现在正在编写一段代码,如下所示:

static runtime_thread *t0;

void 
queue_thread (runtime_thread *newt)
{
   t0 = newt;
   do_something_else ();
}

void 
kill_and_replace_thread (runtime_thread *newt)
{
   t0->status = dead;
   t0 = newt;
   t0->status = runnable;
   do_something_else ();
}

注意:将以上内容视为某种混合的 C 和伪代码,让您了解全局在哪里实际有用。

于 2013-08-31T11:42:09.543 回答
0

在编写任何跨平台库时,静态全局几乎是必需的。这些全局变量是静态的,因此它们保留在翻译单元中。很少有跨平台库不使用静态全局变量,因为它们必须向用户隐藏其平台特定的实现。这些平台特定的实现保存在静态全局变量中。当然,如果他们使用不透明指针并要求将平台特定的实现保存在这样的结构中,他们可以制作一个没有任何静态全局的跨平台库。但是,需要将这样的对象传递给此类库中的所有函数。因此,你必须到处传递这个不透明的指针,或者制作静态全局变量。

还有标识符限制问题。编译器(尤其是较旧的编译器)对它们在一个范围内可以处理的标识符数量有限制。许多操作系统仍然使用大量的#define而不是enum迭代,因为它们的旧编译器无法处理使标识符膨胀的枚举常量。适当重写头文件可以解决其中的一些问题。

于 2020-02-25T16:06:53.580 回答
-1

当您想在包括 main 在内的每个函数中使用全局变量时,都会考虑全局变量。还要记住,如果你全局初始化一个变量,它的初始值在每个函数中都是相同的,但是你可以在函数内部重新初始化它,以便在该函数中为该变量使用不同的值。这样,您不必在每个函数中一次又一次地声明相同的变量。但是,是的,它们有时会造成麻烦。

  • 项目清单

全局名称随处可见。当您认为您正在使用本地时,您可能会在不知不觉中最终使用全局

  • 如果您在声明全局变量时出错,那么您将不得不将更改应用到整个程序,就像您不小心将其声明为 int 而不是 float
于 2013-08-31T13:23:27.227 回答