在多个函数中使用同一个大数组而不冗余的正确方法


Proper way to use the same large array in multiple functions without being redundant?

我没有要处理的特定情况,所以请将其视为一个更一般的问题。如果语言很重要,答案可能更倾向于PHP。

如果我有一个大数组(或其他数据类型)的数据,我需要在多个函数中使用,这不会改变,我应该如何使用这些数据?例如,也许我有一个看起来像的数组

$states = array(
                "AL" => "Alabama",
                     ...
                "WY" => "Wyoming"
                );

显然,这个数组不需要在短期内更改。如果我有五个函数必须使用上面的数组,那么最好的解决方案是什么?我的三个想法是:

  • 将其声明为全局常量

这似乎是最直接的,然而,与我交谈过的一些人似乎建议避免使用全局变量。如有任何见解,我们将不胜感激。

  • 将其传递到函数中

这个对我来说似乎是个坏主意,因为它永远不会改变,函数参数应该用于变量,对吧?更不用说必须将它传递给一个不使用它的函数,这样它就可以被另一个函数使用。这似乎是一种糟糕的做法。

  • 是否由函数返回

这是一个我很少使用的函数,但我已经用过几次自己将mysqli_connect()信息传递给多个函数。它运行得很好。这是否被视为不良做法?我应该接受它并使用全局常数吗?

我意识到使用全局常数听起来很明显,但我听过(也读过)不止一句口头禅,比如"如果你在声明全局变量,你就做错了"之类的话。有人能解释为什么会这样吗?

谢谢你们能给我的任何见解,伙计们。

我的一般建议是构建一个"服务提供者"类,类似于"从函数返回"选项。以下是一些具体的想法:

  • 将其声明为全局常量

首先,常量只能是标量值,所以从技术上讲,不能有"常量"数组。其次,你所说的几乎总是正确的:全局变量暗示有更好的方法(除了一些例外)。

  • 将其传递到函数中

如果它们实际上是常数(在"现实世界"意义上,而不是计算机科学意义上),那么你是对的,传递给函数应该被视为代码混乱(除非函数应该从"全局"值的知识中抽象出来,但这是特定领域的架构选择。

  • 是否由函数返回

丁丁!原因本质上是这样的:任何人都可以访问这些来"读取",但只有"函数"可以"写入"。我把"function"放在引号里,因为它也可以是类或单例对象实例。基本上,您提供了这个静态信息的语义适当的提供者。

这种方法的好处之一是,在长时间运行的程序中,您可能只需要很少的数据。在这种情况下,服务提供者可以被编写为从一些内存外持久性中获取值,并在不再需要内存时释放内存。没有其他人应该负责内存管理。同样,想象一下项目的增长,这些数据需要从数据库而不是静态数组中加载。。。如果您集中了访问,这非常容易实现,而且您不需要在程序执行的整个长度上有一大堆内存,这些内存中包含几乎从未访问过的值。

如果你坚持不使用全局变量(这确实是一个坏习惯!),那么你可以将其"隐藏"在一个函数中:

function get_state($state_code){
  static $states = array(
                "AL" => "Alabama",
                     ...
                "WY" => "Wyoming"
                );
  return $states[$state_code];
} 

但是,在这种情况下,在我看来,使用全局数组就可以了,有点像在Java中创建Enam。

听起来像是包装类将那些明显相关的函数捆绑在一起:

class CountryHelper {
    protected static $states = array('AL' => ..., ...);
    public function foo() {
        self::$states ...
    }
    public function bar() {
        self::$states ...
    }
}

这取决于您所处的环境-在MVC中,我会将其作为Controller的静态属性注入,以便您可以通过以下方式访问它:

 $this -> settings('states')[$state];

否则,我只会使用Settings类的静态字段:

 class Settings
 {
      static $states = array( ... );
 }

或者,即使在脚本启动时填充了singleton,如果需要,也可以从其他地方加载设置[yaml/ini]——尽管在我看来,singleton使用不是一个好的做法。

无论如何,不要全局化,请始终正确命名vars/函数的名称空间。