什么时候全局变量被认为是好的/推荐的做法



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

所以我的问题是,为什么仍然需要全局变量,它们是否提供了一些无法替代的独特和不可替代的优势?与用户指定的从本地作用域中检索对象的自定义间接寻址相比,全局寻址有什么好处吗?

据我所知,在现代编程语言中,全局寻址与计算内存地址的每个偏移量具有相同的性能损失,无论是从"全局"用户内存开始的偏移量,还是从this或任何其他指针的偏移量。因此,就性能而言,用户可以使用公共指针间接寻址在需要的狭窄情况下伪造全局变量,而不会将性能输给真正的全局变量。那还有什么?真的需要全局变量吗?

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

基本上,变量的范围应该只是代码工作和相对容易理解所需的范围,而不是更多。将全局变量放在打印出十二个时间表的程序中是可以管理的,将它们放在数百万行的会计程序中就不那么好了。

我认为这是另一个类似于goto的主题——这是一个"宗教的东西"。

有很多方法可以"绕过"全局变量,但如果您仍在代码中的不同位置访问相同的内存,则可能会出现问题。

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

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

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

然而,作为一个整体,我建议避免使用global。

全局变量表示全局状态。这使得无法在程序中存储给定零件或函数的本地重叠状态。

例如,让我们留下来,我们将给定用户的凭据存储在整个程序中使用的全局变量中。现在要升级我们的程序以允许多个用户同时使用会困难得多。如果我们只是将用户状态作为参数传递给我们的函数,那么升级到多个用户的问题就会少很多。

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

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

例如,我现在正在编写一段代码,它看起来像这样:

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和伪代码的混合代码,让您了解全局代码的实际用途。

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

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

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

  • 列出项目

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

  • 如果您在声明全局变量时犯了错误,那么您将不得不将更改应用于整个程序,就像您意外地将其声明为int而不是float一样

相关内容

  • 没有找到相关文章

最新更新