Есть ли способ переназначить $ this? - PullRequest
4 голосов
/ 14 января 2010

Прежде всего, я не хочу расширять класс. В идеале я бы хотел это сделать.

public function __construct() {
 /* Set Framework Variable */
 global $Five;
 $this =& $Five;
}

У меня есть система, где переменная $ Five - это контейнерный класс, который содержит другие библиотеки. Я мог бы присвоить это локальной переменной Five ... т.е.

public function __construct() {
 /* Set Framework Variable */
 global $Five;
 $this->Five = $Five;
}

Однако причина, по которой я пытаюсь избежать этого, заключается в том, что вызовы функций будут немного длиннее.

$this->Five->load->library('library_name');

Это немного некрасиво. Гораздо лучше было бы.

$this->load->library('library_name');

Каково лучшее решение для этого?

Ответы [ 7 ]

5 голосов
/ 14 января 2010

Я думаю, что

$this->Five->load->library('library_name');

будет вашим лучшим вариантом, если вы не решите, чтобы класс расширял вспомогательный класс. AKA

class Something extends Helper_Class

Однако это означает, что Helper_Class создается каждый раз, когда вы создаете экземпляр класса.


Другим методом может быть псевдостатический класс, который назначит все вспомогательные классы членам класса

public function setGlobals($five)
{
    $this->loader = $five->loader;
}

Тогда просто назовите это

public function __construct($five)
{
    someClass::setGlobals($five);
}

Если $Five является глобальным, вы можете просто global $Five каждый раз, когда захотите его использовать, но ставить его во главе каждой функции просто кажется плохим кодированием.


Кроме того, я просто хотел бы сделать мое публичное объявление о том, что глобальные переменные, как правило, являются плохой идеей, и вы можете искать «Внедрение зависимостей» или альтернативу глобальным переменным. AKA

public function __construct($five);

вместо

global $five;

Глобальные переменные полагаются на внешнюю переменную, которая должна присутствовать и уже установлена, в то время как внедрение зависимостей запрашивает переменную, которая, как предполагается, является экземпляром класса Five.

Если вы используете PHP 5.1 (спасибо Гордон), вы можете убедиться, что переменная является экземпляром FiveClass, выполнив следующее:

public function__construct(FiveClass $five);
2 голосов
/ 14 января 2010

$ это ссылка на текущий экземпляр класса, который вы определяете. Я не верю, что вы можете назначить это. Если Five является глобальным, вы должны просто сделать это:

$Five->load->library('library_name');
1 голос
/ 14 января 2010

Вы не можете перезаписать $ this (как, например, в C ++), но вы можете легко построить агрегат , используя __ call () для вызовов методов и __get (), __set (), __isset () для свойств.

Пример для __call ():

class Five {
  public function bar() {
    echo __METHOD__, " invoked\n";
  }
}

class Foo {
  protected $Five = null;

  public function __construct(Five $five=null) {
     if ( is_object($five) ) {
       $this->Five = $five;
     }
   }

  public function __call($name, $args) {
    // there's no accessible method {$name} in the call context
    // let's see if there is one for the object stored in $five
    // and if there is, call it.
    $ctx = array($this->Five, $name);
    if ( !is_null($this->Five) && is_callable($ctx) ) {
      return call_user_func_array($ctx, $args);
    }
    else {
      // ....
    }
  }
}

$foo = new Foo(new Five);
$foo->bar();

отпечатков Five::bar invoked.
На мой взгляд, самым большим недостатком является то, что гораздо сложнее увидеть «извне», на что способен объект.

1 голос
/ 14 января 2010

Как насчет создания соответствующих членов-данных и методов из пяти статических членов класса? Это

$this->Five->load->library('library_name');

станет этим

Five::load->library('library_name');

и вам не нужно будет пропускать и $ пять вокруг.

1 голос
/ 14 января 2010

Возможно, вы захотите пойти по пути реализации шаблона внедрения зависимостей:

Внедрение зависимостей (DI) в компьютер программирование относится к процессу поставляя внешнюю зависимость программный компонент. Это конкретный форма инверсии управления, где беспокойство перевернутый процесс получения необходимой зависимости.

См. Также документацию для контейнера symfony DI . Я настоятельно рекомендую эту реализацию контейнера DI, если вы хотите улучшить способ обработки ваших глобальных переменных.

Вы также можете прочитать этот вопрос о «лучших способах доступа к глобальным объектам».

0 голосов
/ 14 января 2010

может лучше для вас будет использовать PHP Magic Methods? http://www.php.net/manual/en/language.oop5.overloading.php#language.oop5.overloading.methods

0 голосов
/ 14 января 2010

Я почти уверен, что вы не можете переназначить $this, так как это одна из тех особых вещей, которая выглядит как переменная в PHP, но рассматривается немного иначе за кулисами.

Если ваши проблемысемантика вашего вызова метода становится слишком длинной, я бы сделал load вызов метода вместо свойства объекта

$this->load()->library('library_name');

public function load()
{
    return $this->Five;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...