【问题描述】:

我注意到 PHP 中有两种方法可以做同样的事情。你能告诉我哪种方式是更好的编程习惯吗?

在第一个示例中,我在类上使用了一个私有变量。在第二个示例中,我在类方法中使用了一个静态变量。

class Test {
  private $_myvar;
  public function getVar(){
    if (!isset($this->_myvar)) {
      $this->_myvar = "test\n";
    }
    return $this->_myvar;
  }
}
$oTest = new Test();
echo $oTest->getVar(); // sets var first time and returns it
echo $oTest->getvar(); // pulls from cache

或者:

class Test {
  public function getVar(){
    static $myvar;
    if (!isset($myvar)) {
      $myvar = "test\n";
    }
    return $myvar;
  }
}
$oTest = new Test();
echo $oTest->getVar(); // sets var first time and returns it
echo $oTest->getvar(); // pulls from cache

【问题讨论】:

  • 在您的第一个示例中,它不应该说 $this->_myvar 而不是 $_myvar?
  • “私人”部分没有区别;公共和受保护的类属性也存在相同的行为。
  • @El Yobo,对,但是拥有公共变量的访问器会很愚蠢。 :)
  • @bumperbox - 我的错 - 错字。谢谢!我会编辑。
  • 这很愚蠢,是的 :) 我只是指出“私人”不会改变这里的行为。例如,有一个受保护变量的访问器是有意义的;但无论是否有意义,行为都是一样的。

标签: php class variables static private


【解答1】:

使用类属性(无论是公共的、私有的还是受保护的),类的其他部分都可以访问该变量。

使用静态变量,它只对类的该方法可见。

我建议使用类属性(但可能不是私有的,我通常不会发现它有太多用处;受保护通常是一个更好的主意),因为以后测试更容易;你不能做任何事情来取消、改变或检查静态变量。

我在 static variablesstatic class properties 之间的其他答案中看到了一些可能的混淆。 PHP 使用相同的修饰符,但行为完全不同;下面是一个例子。

<?php
class Foo {
   // Static class property
   public static $bar = 'bar';

   public function blarg() {
      static $bar;
      if (empty($bar)) {
         $bar = 'blarg';
      }
      return $bar;
   }
}

在上面的示例中,静态类属性可以使用 Foo::$bar(或类中的 self::$barstatic: :$bar 在 PHP 5.3);静态变量 cannot 并且仅在函数 blarg() 内可见。

【问题讨论】:

  • 我意识到这是一个奇怪的问题。您必须查看我正在使用的代码才能实现上下文。但是您让我意识到,是的,静态变量只能由类方法访问。实际上,无论如何,只有一个类方法需要访问该变量。在这个项目的代码的另一部分中,我有 - 使用私有(现在受保护)var 是有意义的,因为需要多个类方法来访问它。
  • 另请参阅下面 Orbling 的评论,该评论提供了有关对象方法中静态变量的奇怪(而且在我看来,非常不受欢迎)行为的更多详细信息。
【解答2】:

这就像说厨房和浴室哪个房间更好,它们都是房间,但功能不同。

一个static变量在多个对象中是相同的。

通过上面的 private 声明的实例变量特定于给定对象。

注意private是访问修饰符,static不是,变量可以两者兼有。

在你有 static 变量的位置,在函数中,它根本不是类/对象变量,而是传统的函数级 static 变量,它将在对函数的所有调用中为单一实例,使其类似于类级别的 static 变量,但只能在定义它的方法内访问。

【问题讨论】:

  • 我认为您在这里将静态类属性与静态变量混淆了; PHP 使用相同的修饰符,但行为完全不同。
  • @aharon 我刚试过这个,我很确定静态变量会在多个对象中持续存在。
  • 嗯,你每天都会学到新东西; Sabeen 是正确的,方法 中的静态变量在对象之间共享。这一定是一些真正令人困惑的错误的根源!更有理由不使用它;在一个实例中修改它会神奇地在另一个实例中更改它。
  • @El Yobo:在类方法中使用静态变量是您在 PHP 4 中使用静态类变量的方式。这有点笨拙,可能还有意想不到的副作用,但它确实有效。< /跨度>
  • 我在 PHP4 中突破了 OO 的界限。 :-) 实例方法具有静态变量是完全合法的,因为它们是使用一种带有隐藏的第一个参数的名称修饰来实现的。如果它从未引用过 $this,那么您可以 静态调用这样的方法(class::func())。就像我说的,笨重。但它奏效了。
【解答3】:

两者都不是“更好”。这就像问螺丝刀是否比榫锯更好。

您的第一个示例中的私有变量将仅可用于该类的该实例(尽管仅可用于其方法)。创建一个新实例,该变量可以并且将具有不同的值。

第二个示例中的静态变量将可用于该类的所有实例,不可否认,仅在该方法中。但是设置一个实例,第二个实例将看到相同的值。

【问题讨论】: