4

关于在类中使用全局函数的问题,我正在研究 MVC 系统。

以下方法是类的一部分,它调用类中的方法,例如模型和视图我的问题是我在那里有一个名为 redirect() 的全局函数bootstrap 文件,因为所有控制器都可能需要访问它,这是一种不好的做法,还是我最好将其作为控制器类的方法,因为所有控制器都扩展了父控制器。

public function post($slug){

  if(!$slug){ redirect('blog'); }

  $data = $this->model->getPost($slug);
  $this->view->render('blog/single', $data);
}

还是静态类更有意义?对于一个简单的重定向功能来说,这似乎有点过头了。

4

3 回答 3

7

全局函数不一定是坏习惯。有两点需要注意:

命名:您应该确保函数的名称避免冲突并且与其相关的内容很明显。您的重定向功能,预计它会执行请求重定向。相反,如果您的方法与其他更具体的方法相关,则需要通过预先添加一些上下文信息来明确情况就是如此。

状态:全局函数应该是无状态的。这意味着该函数应始终为给定的输入提供相同的结果。如果它根据一天中的时间、某些变量的值等做不同的事情……那么通常这是不好的。这可能看起来像是一个明显的陷阱,但这个问题还有更微妙的版本。该规则的明显例外实际上是请求一天中的时间......

看起来你的代码遵循这两个规则,所以这样做是完全可以接受的。

编辑存在可测试性问题,因为您正在引用该类(或应该)需要的全局函数,您不能模拟它。例如,在您的重定向示例中,如果不触发重定向函数,您将无法正确测试该类,并且您不能使用该函数的模拟版本来检测是否会调用真正的重定向方法。

于 2012-12-30T23:49:37.113 回答
2

使用全局函数是不好的做法,因为它会使你的类无法测试。您应该将所需的方法放在某个对象上,并将其作为依赖项传递给类。

于 2012-12-30T23:43:01.220 回答
1

正如您在评论中指出的那样,它是一个很小的单行方法,如果您使用 PHP 5.3,而不是全局,最好使用 lambda 函数并将其传递,而不是创建一个全新的类。

我会尝试设计代码,以便注入依赖项,并可能将引导程序暴露给控制器并在其中存储一个 lambda,然后在你想要的地方调用它。

有关 lambda 的使用,请参阅http://fabien.potencier.org/article/17/on-php-5-3-lambda-functions-and-closures,DI示例也有望提供一些见解。

于 2012-12-31T01:34:48.160 回答