【问题标题】:PHP - class forget set variablesPHP - 类忘记设置变量
【发布时间】:2012-10-23 03:15:00
【问题描述】:

我尝试创建某种设置类,例如页面的全局值。

PHP 代码

class globals
{
    public $page;

    public function __construct()
    {
    }

    public function set_page($value)
    {
        $this->page = $value; // Maybe from a database
    }
}

class get
{
    public function page()
    {
        $globals = new globals();
        return $globals->page;
    }
}

$globals = new globals();
$globals->set_page('My value');

echo get::page(); // Short function to be in a template

问题

  • 我的班级忘记了我设置的值。这是为什么呢?
  • 我必须使用全局变量吗?
  • 这是解决问题的正确方法吗?

【问题讨论】:

  • 必须设置页面,才能获取页面。

标签: php class scope global


【解决方案1】:

变量是在对象上设置的,而不是在类上。

对于每个类,您可以实例化多个对象。每个都有自己的变量范围。

【讨论】:

    【解决方案2】:

    要使用没有对象的类的方法,您必须使用 static 定义。但无论如何,你为一个类对象赋值并尝试从另一个类对象中获取它......

    【讨论】:

      【解决方案3】:

      我必须使用全局变量吗?

      不,如果你可以使用 PHP 5.3

      这是解决问题的正确方法吗?

      最好为此使用泛型类,或者使用对象的静态属性

      <?php
      
      class globals
      {
          public static $page;
      
          public function __construct()
          {
          }
      
          public function set_page($value)
          {
              self::$page = $value; // Maybe from a database
          }
      }
      
      class get
      {
          public static function page()
          {
              return globals::$page;
          }
      }
      
      $globals = new globals();
      $globals->set_page('My value');
      
      echo get::page(); // Short function to be in a template
      

      附: 但这不是一个好的方法

      【讨论】:

      • 那行得通。保留 get::page() 对我来说很重要。有什么比我更好的方法?
      • @JensTörnell:你为什么认为get::page()很重要...如果所有这些代码都告诉你当前页面是什么,你可以定义一个常量BTW:1行defined('CURRENT_PAGE') || define('CURRENT_PAGE','My Value');。基本上,这会检查是否设置了常量,如果没有,它会定义它,并将值设置为My Value。常量在全局范围内可用,并且使用的资源不如类
      【解决方案4】:

      $globals那里

      class get
      {
          public function page()
          {
              $globals = new globals();
              return $globals->page;
          }
      }
      

      还有

      $globals = new globals();
      $globals->set_page('My value');
      

      globals 类的不同实例。

      其中一种解决方案是将$page var 设为静态

      public static $page;
      

      希望对你有帮助

      UPD:

      您也可以将 Singleton 应用于全局类并请求其实例,而不是直接创建新实例:

      globals::getInstance()->setPage('Page');
      

      return globals::getInstance()->getPage();
      

      在这种情况下,$page 不必是静态的。

      【讨论】:

        【解决方案5】:

        编辑:
        我忘了包括对您的问题的最简单、最不冗长的解决方案。 AFAIK,您正在寻找一种方法来检查您所在的页面。常量就是这样做的:

        defined('MY_CURRENT_PAGE') || define('MY_CURRENT_PAGE','My Value');
        //use anywhere like so:
        echo 'Currently on page: '.MY_CURRENT_PAGE;
        

        我的班级忘记了我设置的值。这是为什么呢?

        很简单:您的page 成员函数不是静态的,但您将其称为:get::page()。即使你要解决这个问题,你也在 page 方法中创建一个新实例,但你没有在任何地方保留一个引用,所以每个 page 调用都会创建一个新的 globals 实例,即没有设置。

        我必须使用全局变量吗?

        不,除非你真的绝望,否则永远不要使用全局变量

        这是解决问题的正确方法吗?

        不,如果它不起作用,那是不正确的(恕我直言)。

        嗯,是什么,你可能会问。有几种方法可以解决这个问题:

        class globals
        {
            public static $page = null;//make this static, meaning all instances will share this var
        
            public function set_page($value)
            {
                self::$page = $value; // Maybe from a database
            }
        }
        
        class get
        {
            private $_globalsInstance = null;
            public function __construct(globals $instance = null)
            {
                $this->_globalsInstance = $instance;
            }
        
            private function _getGlobals()
            {
                if (!$this->_globalsInstance instanceof globals)
                {
                    $this->_globalsInstance = new globals();
                }
                return $this->_globalsInstance;
            }
        
            public function page()
            {
                return $this->_getGlobals()::$page;
            }
        }
        

        然而,就我个人而言,我不会这样工作,我只是将我的实例传递到我需要它们的任何地方(作为函数/方法的参数,或者只是在可访问的范围内实例化它们:

        class globals
        {
            public $page = null;//make this static, meaning all instances will share this var
        
            public function set_page($value)
            {
                $this->page = $value; // Maybe from a database
            }
        }
        $page = new globals();
        $page->set_page('foobar');
        someFunction($page);
        $someObject->renderPage($page);
        require_once('specificScript.php');
        //inside required script:
        echo $page->page;
        

        【讨论】:

          【解决方案6】:

          我不确定其他答案是否非常清楚。您已经创建了 2 个类。因此,它们具有不同的范围。正如所写的那样,您无法从 get 类访问原始变量 $page ,因为它超出了范围。您的 page 函数实际上创建了对象 $globals 的新版本,而没有设置 $page 。通常,您会将 set 和 get 函数都放在初始对象/类中。虽然可以通过从第二个类调用第一个类并设置页面来使用两个类。我不确定你为什么要这样做。

          如果我正在编写课程,它会是这样的。

          class globals
          {
              public $page;
          
              public function __construct()
              {
              }
          
              public function set_page($value)
              {
                  $this->page = $value; // Maybe from a database
              }
          
              public function get_page()
              {
                  return $this->page;
              }
          }
          

          实际上,我可能会将页面设置为私有而不是公开。作为公众,我猜你不需要 get 函数。

          【讨论】:

            【解决方案7】:

            也许这会帮助你继续你的粗略:

                 class globals
                 {
                    public static $page;
            
                    public function set_page($value)
                    {
                       self::$page = $value; // Maybe from a database
                    }
                 }
            
                class get extends globals
               {
                  public function page()
                 {
                    $globals = new globals();
                    return parent::$page;
                 }
               }
            
               $globals = new globals();
               $globals->set_page('My value');
            
               echo get::page();
            

            ?>

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 1970-01-01
              • 2011-12-18
              • 1970-01-01
              • 2012-04-11
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多