ООП динамическое добавление методов

Статус
В этой теме нельзя размещать новые ответы.

CrashX

В прошлом XSiteCMS
Регистрация
6 Июн 2008
Сообщения
682
Реакции
114
ООП динамическое добавление методов
может кто делал ранее
нужно скажем есть свойство
keyword и нужно его сделать методом и назначить набор свойст вида
get,set,generate,clear
щас имею вид
Код:
$engine->document->keySet();
$engine->document->keyGet();
$engine->document->keyGen();
а хочу
внутри должно быть
Код:
private $value=array();
$engine->document->key->generate();
$engine->document->key->get();
$engine->document->key->set();

набор действий стандартных одинковый это вернуть ключ, добавить ключ, создать, очистить.

как нибудь можно скажем имея шаблон расширять нужные свойства до объектов

зачем это нужно ? да тупо для удобства
тк мне удобнее обращаться к некоторому свойству не трогая его само что бы голова не болела что могу его испортить

такую фигню хочу добавить массово многим объектам
 

chang

Постоялец
Регистрация
20 Ноя 2009
Сообщения
363
Реакции
118
ну так сделайте внутреннюю переменную key каким-то классом (на подобии паттерна Registry ) внутри которого будут реализованы все эти методы get,set,generate,clear

или я чего-то не то понял?
 

saen

Постоялец
Регистрация
6 Авг 2006
Сообщения
756
Реакции
129
ну так сделайте внутреннюю переменную key каким-то классом (на подобии паттерна Registry ) внутри которого будут реализованы все эти методы get,set,generate,clear

или я чего-то не то понял?
То что ТС хочет реализовать, называется метапрограммирование, которое в PHP отсутствует. Можно попробывать сделать эмуляцию метапрограммирования через создание анонимных лямбда-функций либо попробовать поиграть с дополнением php runkit.
 

CrashX

В прошлом XSiteCMS
Регистрация
6 Июн 2008
Сообщения
682
Реакции
114
в общем как хотел не смог сделал проще
сделал для каждого метода, который нужно расширить и расширил в конструкторе.
благо еще раз подумал и сделал там где действительно нужно скрыть
например

PHP:
<?php


/**
 * Класс документа
 */
class Document {

  var $version = 0.01;
  public $title = null;
  public $description = null;
  public $keyword = null;
  public $style = null;
  public $script = null;
  public $header = null;

  public function __construct() {
    $this->keyword = new Keyword();
    $this->description = new Description();
    $this->title = new Title();
  }

  /**
   * @global Engine $engine
   */
  function headers() {
    global $engine;
    header("Content-Type: text/html; charset=" . $engine->language->get('CHARSET'));
    header("Cache-Control: no-store, no-cache, must-revalidate");
    header("Cache-Control: post-check=0, pre-check=0", false);
    header("Pragma: no-cache");
    header("Expires: " . gmdate("D, d M Y H:i:s", 0) . " GMT");
    header("Last-Modified: " . gmdate("D, d M Y H:i:s") . " GMT");
    header("X-Powered-By: XSiteCMS ");
  }

  /**
   * @global Engine $engine
   * @return <type>
   */
  function meta() {
    global $engine;
    return '<meta charset=' . $engine->language->get('CHARSET') . ' />
  <meta http-equiv="content-type" content="text/html; charset=' . $engine->language->get('CHARSET') . '" />
  <meta name="title" content="' . $this->title->get() . '" />
  <meta name="keywords" content="' . $this->keyword->get() . '" />
  <meta name="description" content="' . $this->description->get() . '" />
  <meta name="abstract" content="' . $this->description->get() . '" />
  <meta name="generator" content="' . GENERATOR . '" />'
    . (GOOGLE ? "\n" . '  <meta name="verify-v1" content="' . GOOGLE . '" />' : '')
    . (YANDEX ? "\n" . '  <meta name="yandex-verification" content="' . YANDEX . '" />' : '')
    . (WEBMONEY ? "\n" . '  <meta name="webmoney.attestation.label" content="' . WEBMONEY . '" />' : '')
    . "\n" . '  <link rel="alternate" href="feed.rss" type="application/rss+xml">
  <link rel="icon" href="favicon.ico" type="image/x-icon">
  <link rel="shortcut icon" href="favicon.ico" type="image/x-icon">';
  }
}

/**
 * Класс ключевых влов
 */
class Keyword {

  var $version = 0.01;
  public $config = array('words' => 15, 'min' => 5, 'max' => 25);
  private $keywords = array();
  private $endings = array("ые", "ое", "ие", "ий", "ая", "ый", "ой", "ми", "ых", "ее", "ую", "их", "ым");
  private $exceptions = array("able", "about", "даже", "дал", "далее", "далеко"
  );

  /**
   *
   * @global Engine $engine
   */
  public function __construct() {
    global $engine;
    $this->keywords = preg_split("/[\s,]+/s", $engine->string->trim($engine->config['keywords']));
  }

  /**
   *
   * @global Engine $engine
   */
  function get() {
    global $engine;
    return (string) implode(", ", $this->keywords);
  }

  /**
   *
   * @global Engine $engine
   * @param <type> $key
   */
  function set($key) {
    global $engine;
    if (in_array($key, $this->keywords)):
      return false;
    else:
      $this->keywords[] = $key;
    endif;
  }

  /**
   *
   * @global Engine $engine
   */
  function clear() {
    global $engine;
    $this->keywords = array();
  }

  /**
   *
   * @global Engine $engine
   * @param string $text
   * @return mixed
   */
  function generate($text=null) {
    global $engine;
    $text = $engine->string->lower($text);
    // вырезаем теги, символы и лишние пробелы
    $text = $engine->string->clean($text);
    // создаем массив слов
    $words = preg_split("/[\s]+/s", $text);
    ...
    return $words;

  }

}

/**
 * Класс составления описания страницы
 */
class Description {

  var $version = 0.01;
  public $config = array('length' => 300);
  private $description = array();
  private $synonyms = array('searche' => 'replace');

  /**
   *
   * @global Engine $engine
   */
  public function __construct() {
    global $engine;
    $this->description = $engine->config['description'];
  }

  /**
   *
   * @global Engine $engine
   * @param <type> $key
   */
  function get() {
    global $engine;
    return $this->description;
  }

  /**
   *
   * @global Engine $engine
   * @param <type> $key
   */
  function set($string) {
    global $engine;
    $this->description .= $string;
  }

  /**
   *
   * @global Engine $engine
   */
  function clear() {
    global $engine;
    $this->description = null;
  }

  /**
   *
   * @global Engine $engine
   * @param string $text
   * @return mixed
   */
  function generate($text=null) {
    global $engine;
  }

}

/**
 * Класс заголовка страницы
 */
class Title {

  var $version = 0.01;
  public $config = array('length' => 300, 'separator' => ' - ');
  private $title = array();
  private $synonyms = array('searche' => 'replace');

  /**
   *
   * @global Engine $engine
   */
  public function __construct() {
    global $engine;
    $this->title[] = $engine->config['title'];
  }

  /**
   *
   * @global Engine $engine
   * @param <type> $key
   */
  function get() {
    global $engine;
    return (string) implode($this->config['separator'], $this->title);
  }

  /**
   *
   * @global Engine $engine
   * @param <type> $key
   */
  function set($string) {
    global $engine;
    $this->title[] = $string;
  }

  /**
   *
   * @global Engine $engine
   */
  function clear() {
    global $engine;
    $this->title = null;
  }

  /**
   *
   * @global Engine $engine
   * @param string $text
   * @return mixed
   */
  function generate($text=null) {
    global $engine;
  }

}

//
?>
 

LEE_ROY

Местный житель
Регистрация
26 Янв 2007
Сообщения
205
Реакции
21
не совсем вник в задачу, но кейворд можно сделать отдельным классом с методом __toString который позволит обращаться к кейворду как к обьекту так и к строке где нужно.
 

CrashX

В прошлом XSiteCMS
Регистрация
6 Июн 2008
Сообщения
682
Реакции
114
магические методы в этом случае ненужны, ими пользоватся умею...
увы то что хочется нельзя делать в пхп, да и нужна как то отпала...
нужно было расширение нужных свойст до методов со стандартным набором действий, и защищенным хранилищем внутри.
 

saen

Постоялец
Регистрация
6 Авг 2006
Сообщения
756
Реакции
129
магические методы в этом случае ненужны, ими пользоватся умею...
увы то что хочется нельзя делать в пхп, да и нужна как то отпала...
нужно было расширение нужных свойст до методов со стандартным набором действий, и защищенным хранилищем внутри.

Пару замечаний по твоему коду:
1)
PHP:
return (string) implode(", ", $this->keywords);
зачем приводить к типу "string", если ф-я implode итак возвращает строку?

2) Есть такой паттерн проектирования как регистр(registry), который представляет из себя единое глобальное хранилище. На твоем месте я бы отказался от использования глобальных переменных в ф-ии в пользу регистра.

И еще по поводу твоей задачи: с выходом новой ветки php(5.4 или 6) появится поддержка traits(для непрошаренных это значит множественное наследование). Да и про импорт-оператор "use" ты наверняка не слышал...
 

CrashX

В прошлом XSiteCMS
Регистрация
6 Июн 2008
Сообщения
682
Реакции
114
у меня и так подобие но только без __clone
у меня однократная инициализация, вот иногда нужно перезагружать класс с другим расширением но пока не придумал как,
поэтому у меня большая зависимость между классами, 50% мелких классов самодостаточна но более крпные прямолинейно зависят от мелких...
хранилищем у меня выступает корневой класс Engine в который загружаются новый классы при обращении к несуществющему свойству, методу и тп...

про (string) да приведение, поидее нужно делать именно так но у нас мало кто так делает, да и там не полный набор показан, часть просто вырезана.
 

saen

Постоялец
Регистрация
6 Авг 2006
Сообщения
756
Реакции
129
у меня и так подобие но только без __clone
у меня однократная инициализация, вот иногда нужно перезагружать класс с другим расширением но пока не придумал как,
поэтому у меня большая зависимость между классами, 50% мелких классов самодостаточна но более крпные прямолинейно зависят от мелких...
хранилищем у меня выступает корневой класс Engine в который загружаются новый классы при обращении к несуществющему свойству, методу и тп...

про (string) да приведение, поидее нужно делать именно так но у нас мало кто так делает, да и там не полный набор показан, часть просто вырезана.
так почему надо делать приведение к типу "string", если ф-я implode итак возвращает строку?
 

CrashX

В прошлом XSiteCMS
Регистрация
6 Июн 2008
Сообщения
682
Реакции
114
да и там не полный набор показан, часть просто вырезана.
у меня часть кода вырезана... там вызов еще некоторых ключей)
(int)(string) по большей части, привычка писать...
просто где то читал что типа так нужно... да и сам не читаю что они возвращают, а то есть и mixed) а так поменяю чего и все будет все равно норм)
 
Статус
В этой теме нельзя размещать новые ответы.
Сверху