[ Поиск ] - [ Пользователи ] - [ Календарь ]
Полная Версия: М. Зандстра. Глава 9. стр. 167
m4a1fox
М. Зандстра. Глава 9. стр. 167.
Итак, если все пойдет по плану, то планирую с этого шаблона начать цикл статей посвященных шаблонам в php, или,
как их еще называют - паттерны.
Трезво оценив все свои возможности, я буду стараться выкладывать разбор шаблонов не реже одного в неделю.
Если кому то кажется, что это много времени, сразу отвечу. Вы можете сделать быстрее? Делайте.
И еще. Думаю неделю на разбор одного шаблона - вполне достаточный срок что бы каждый с форума мог
высказаться. Итак. Сам пост будет выглядеть следующим образом.
1. Первое будет идти определения. (Наверно не будем експерементировать, и возьмем определения с php.net).
2. Будет идти текст - вырезки из книги.
3. Далее будет идти пример кода, опять же из книги.
4. После реальный пример, кот. можно будет применить на практики. (Поясню: в книжке отличные примеры, но на мой взгляд, уж больно общие.)
5. Что конкретно мне не понятно в шаблонею А таких мест реально много.
6. А после, наверно ссылки. может быть на видео.
В общем как-то так и будет. Что же... а мы начинаем :)
P.S. Пожалуй опущу основы ООП, так как расчитываю. что те кто будут читать это, уже с ними знакомы.


==================================================================================================== ======
// Singletone или шаблон одиночка. //
==================================================================================================== ======

1. Шаблон проектирования Синглтон применяется в тех ситуациях, когда нужно получить единственный
экземпляр класса. Синглтон - один из порождающих шаблонов, описанных "Бандой четырех"
Синглтон обычно применяется в классах для баз данных, логирования, контроллеров(Front Controller) и
объектах, определяющих запросы и ответы(Request и Response).

==================================================================================================== ======

2. Глобальная переменнная - это один из самых больших источников проблем для программиста, использующего ООП.
Глобальные переменные привязываю классы к их контексту, подрывая основы инкапсуляции.
Если в классе используется глобальная переменная, то его невозможно извлечь из одного
приложения и применить в другом, не убедившись сначала, что в новом приложении определяются
такие же глобальные переменные.

==================================================================================================== ======

3.

<?php
class
Preferences{
private $props = array();
private static $instance;

private function __construct(){}

public static function getInstance(){
if(empty(self::$instance)){
self::$instance = new Preferences();
}
return self::$instance;
}

public function setProperty($key, $val){
$this->props[$key] = $val;
}

public function getProperty($key){
return $this->props[$key];
}

}


// Свойство $instance - закрыто и статическое, поэтому к нему нельзя получить доступ из-за пределов класса.
// Но у метода getInstance() есть к нему доступ. Поскольку метод getInstance() - общедоступный и статический,
// его можно вызвать через класс из какого либо места сценария.


$pref = Preferences::getInstance(); // Очень грубо говоря, этот код вернет нам new Preferences();
$pref->setProperty('name', 'Ivan');

unset($pref); // Удаляем ссылку на объект

$pref2 = Preferences::getInstance();
// Убедимся. что ранее установленное значения сохранено
$pref2->getProperty('name');
?>

В результате будет выведенно единственно значение параметра 'name', которое мы ранее добавили к объекту Preferences,
воспользовавшись разными оюбъектными переменными.
==================================================================================================== ======
Ivan
==================================================================================================== ======
Статический метод не может получить доступ к свойствам объектов... но он может получить доступ к статическому свойству.
Когда вызывается метод getInstance() мы проверяем свойство Preferences::$instance. Если оно пусто, то создаем экземпляр
класса Preferences и сохраняем его в свойстве. Затем возвращаем этот экземпляр вызывающему коду. Поскольку статический
метод getInstance() - это часть класса Preferences, у нас нет проблем с созданием экземпляра объекта Preferences,
даже не смотря на то, что конструктор закрытый.

==================================================================================================== ======

4.

Класс соединения с БД.

<?php
class
Database{
private static $driver = 'mysql'; // db drive.
private static $host = 'localhost'; // db host
private static $dbname = 'test'; // db name
private static $dbuser = 'root'; // db user
private static $dbuserpass = ''; // db user pass
private static $connection = NULL; // Свойство кот. устанавливает соединение.

// Делаем приватными конструктор и клонирование.

private function __construct() {}
private function __clone(){}

// Метод getConnection() как понятно из названия, устанавливает соединие с БД
public static function getConnection() {
if (!self::$connection)
{
self::$connection = new PDO(self::$driver."::host=".self::$host."; dbname=".self::$dbname, self::$dbuser, self::$dbuserpass);
self::$connection->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
}
return self::$connection;
}
}


$connect = Database::getConnection(); // соединяемся с БД, если соединения еще нет
$sql = $connect->query("SELECT * FROM user")->fetchAll(PDO::FETCH_ASSOC); // Выполняем запрос на выборку данных
echo '<pre>'.print_r($sql, TRUE).'</pre>'; // Выводим на страницу.
?>

<!--
==================================================================================================== ======

5. Мне например не совсем понятно один момент. Наверно это из-за отсутствия практики, и присутствия неопытности...
Но все же... Ну хорошо! Singleton создается только один раз, собственно в этом то и его суть.
Но что будет если мы его понасоздаем много раз? Память закончится... или что. Что конкретно станется.
Вот собственно что меня беспокоит. Как бы наверно я подозреваю что память, или, что-то еще...
хотелось бы это узнать. Именно логически я не могу понять... ну хорошо, не логически. а больше практически.

6. 1, 2

P.S. Ах да. И еще, господа, если вам не понравилось... то попрошу не перегибать палку со словами, афтар выпей йаду. Просто говорите что вам не нравится и все....



Спустя 16 минут, 16 секунд (14.04.2012 - 22:53) ZSH написал(а):
Цитата
Singleton создается только один раз, собственно в этом то и его суть.

верно
Цитата
Но что будет если мы его понасоздаем много раз?

Вот для того и Singleton чтоб его нельзя было создать много раз

Спустя 4 минуты, 49 секунд (14.04.2012 - 22:58) m4a1fox написал(а):
ZSH
Цитата
Вот для того и Singleton чтоб его нельзя было создать много раз

нет нет! Это как бы понятно! Я тут хотел сказать, что вообще произойдет, если у нас есть класс - не синг, и мы его понасоздаем...

Спустя 5 минут, 59 секунд (14.04.2012 - 23:04) Placido написал(а):
Цитата (m4a1fox @ 14.04.2012 - 23:37)
Синглтон является одним из четырех("Gang of Four") основных создающих шаблонов.

За этот шедевр переводчику нужно руки отбить.
Это неправильный перевод предложения "Singleton is a "Gang of Four" Creational Pattern". Правильно будет где-то так: "Синглтон - один из порождающих шаблонов, описанных "Бандой четырех"".

Спустя 49 секунд (14.04.2012 - 23:05) Oyeme написал(а):
Цитата
Ну хорошо! Singleton создается только один раз, собственно в этом то и его суть.
Но что будет если мы его понасоздаем много раз?


В названии паттерна лежит ответ. ;) "Single"
Вы просто получаете ссылку на обьект.Вы не создаёте объекты кучами.

Update.
На Вашем примере Вы используете класс БД.Для того чтобы не создавать новые объекты каждый раз при обращении к БД Вы получаете ссылку на них.В итоге Вы создаё один объект и у Вас установлена одна связь.

Каждый объект в памяти занимает место.
    $before = memory_get_usage();
$ret = new MyBigClass;
$after = memory_get_usage();
$memory = ($after - $before);

Спустя 2 минуты, 51 секунда (14.04.2012 - 23:08) m4a1fox написал(а):
Placido
Цитата
За этот шедевр переводчику нужно руки отбить.

Спасибо. Поправил!
Oyeme
Цитата
На Вашем примере Вы используете класс БД.Для того чтобы не создавать новые объекты каждый раз при обращении к БД Вы получаете ссылку на них.В итоге Вы создаё один объект и у Вас установлена одна связь.

Спасибо. уже что-то начинает проясняться.
Цитата

Каждый объект в памяти занимает место.

И все таки дело в занимаемой памяти? Ну если грубо говорить?!

Спустя 10 минут, 18 секунд (14.04.2012 - 23:18) ZSH написал(а):
память можно заолнить чем угодно: переменными, массивами, объявлением функций.....
Цитата
Но что будет если мы его понасоздаем много раз?

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

Спустя 2 минуты, 24 секунды (14.04.2012 - 23:20) m4a1fox написал(а):
ZSH
Цитата
тоже что если создать много переменных, объект как-бы переменная у которой есть свои свойства и методы
Ясно. Спасибо! Теперь понятнее.

Спустя 9 минут (14.04.2012 - 23:29) Oyeme написал(а):
Цитата (ZSH @ 14.04.2012 - 21:18)
Цитата

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

Вы путаете понятия что такое переменная и что такое объект.
Переменная - это ссылка на ячейку пямяти.


В зависимости от типа объекта в памяти выделяется количество ячеек памяти, необходимое для размещения объекта.Номер первой из занимаемых объектом ячеек памяти называют адресом объекта.

Спустя 7 минут, 3 секунды (14.04.2012 - 23:36) ZSH написал(а):
Цитата
Вы путаете понятия что такое переменная и что такое объект.

может не так выразился, хотелось чтоб TC понятней было.

Спустя 38 минут, 28 секунд (15.04.2012 - 00:15) Invis1ble написал(а):
в примере с классом для работы с БД синглтон нужен больше не ради экономии памяти, а ради избежания открытия кучи коннектов к БД, когда реально нужен всего один

Спустя 4 минуты, 22 секунды (15.04.2012 - 00:19) m4a1fox написал(а):
Invis1ble
Ну в целом коннект нормально написан?

Спустя 14 минут, 15 секунд (15.04.2012 - 00:34) Invis1ble написал(а):
Цитата
                self::$connection = new PDO(self::$driver."::host=".self::$host."; dbname=".self::$dbname, self::$dbuser, self::$dbuserpass);
                self::$connection->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

переместить в конструктор, а в getConnection создавать и возвращать экземпляр Database (для наглядности переименовать в getInstance)

Спустя 17 минут, 7 секунд (15.04.2012 - 00:51) Invis1ble написал(а):
private static $connection = NULL; - сделать public $connection;
и ввести potected static или private static $_instance для хранения собственно одиночки



Спустя 31 секунда Invis1ble написал(а):
это все мое имхо, если у кого-то другое виденье - пишите

Спустя 8 минут, 53 секунды (15.04.2012 - 01:00) bodja написал(а):
Ужас тихий rolleyes.gif
А чем не устраивает статический класс в качестве одного экземпляра ,и обьекты во множественном числе?

Спустя 1 минута, 19 секунд (15.04.2012 - 01:01) m4a1fox написал(а):
bodja
Цитата
А чем не устраивает статический класс в качестве одного экземпляра ,и обьекты во множественном числе?

Название шаблона этого как?

Спустя 3 минуты, 32 секунды (15.04.2012 - 01:04) bodja написал(а):
Цитата
Название шаблона этого как?

Да никак ,название как название,
если подумать ,то можно и более созвучное название придумать. biggrin.gif

А вообще ,статический класс - это отголосок модульного программирования,который просуществовал недолго и быстро перелился в ООП.
Когда то нельзя было создавать обьект ,но можно было применять класс,методы ,инкапсуляцию и обращатся к нему через пространство имен.
Как по мне - это все по ходу венегрет.
Есть уже нормальные обьекты -ну вот пользуйтесь ими в полный рост не стесняясь. smile.gif

Спустя 9 минут, 34 секунды (15.04.2012 - 01:14) m4a1fox написал(а):
bodja
Ну же... тему то перечитай пожалуйста. Я тут в книге шаблоны пытаюсь разобрать. Ни кто на оригинальность не претендует. И можно делать как ты сказал. Суть не в этом же... а в том, что бы взять книгу и из нее вытаскивать по шаблону. smile.gif

Спустя 2 минуты, 50 секунд (15.04.2012 - 01:17) bodja написал(а):
Не я не против.
Просто это как шаг вперед и два шага назад.

Спустя 6 минут, 34 секунды (15.04.2012 - 01:23) m4a1fox написал(а):
bodja
Ну кто знает. Но суть твою я уловил. Спасибо за информацию.

Спустя 5 часов, 36 минут, 27 секунд (15.04.2012 - 07:00) johniek_comp написал(а):
m4a1fox
Сам меня ругал что бы self не использовал, а тут сам его пишешь! М-да....

А так красевец, продолжай, только про одиночку не интересно, давай другие по сложнее!!!

Спустя 1 час, 20 минут, 32 секунды (15.04.2012 - 08:20) RCuPeR написал(а):
Свернутый текст
Я конечно, извиняюсь, что вмешиваюсь. Но нафига тогда вот эта статья ? Говорили же.

Спустя 49 минут, 6 секунд (15.04.2012 - 09:09) I++ написал(а):
Цитата (bodja @ 15.04.2012 - 03:00)
Ужас тихий rolleyes.gif
А чем не устраивает статический класс в качестве одного экземпляра ,и обьекты во множественном числе?

Солидарен!

Спустя 15 минут, 33 секунды (15.04.2012 - 09:25) I++ написал(а):
По сути и без полемики.

1. Статичный класс или синглтон?

Тут уже нужно подумать, потребуется ли класс расширять трейтами или еще чем и превращать в 1 единственную инстанцию объекта.

Если не требуется, зачем создавать объект? Если можно обращаться к классу без создания объекта, что будет по скорости практически как процедурный подход, за счет того, что нет переключения контекста объектов.

Забота о поддержки кода и защита от дурака, какой смысл? Делать защиту от глупых разработчиков это лишний и ненужный код. Разработчик должен четко понимать, что данный класс статичный и не нужно плодить из него объекты.

Создание "Jimmy-proof" кода, не имеет смысла.

Обычно статичного класса более чем хватает, без лишнего оверхеда.

Спустя 29 минут, 51 секунда (15.04.2012 - 09:55) h234 написал(а):

Спустя 1 час, 17 минут, 34 секунды (15.04.2012 - 11:12) caballero написал(а):
Цитата
Обычно статичного класса более чем хватает, без лишнего оверхеда.

если так рассуждать так и клас тут нафиг не нужен.

Есть большая разница между синглтоном и статическим классом - синглтон создается в момент первого обращения или не создается вообще если не был затребован. А значит не используются лишние ресурсы. При статике ресурсы будут выделятся в момент запуска пролграммы даже если они не появятся.
Конечно в случае PHP конект к БД и так всегда создается - синглтон здесь не более что способ избежать глобальных переменных.
Но в полноценных ООП языках паттерн используется не только для конекта к БД.

Спустя 20 минут, 6 секунд (15.04.2012 - 11:33) glock18 написал(а):
Самый простой паттерн, а у m4a1fox уже столько вопросов. Как будет дальше, даже представить трудно. Думал, что он все хотя бы разберется в вопросе, прежде чем выкладывать что-то, но не тут то было. Ай-ай-ай, нехорошо.

bodja
класс со статическими методами почти тот же самый синглтон, но есть "но" как всегда. Пхп 5.3 появился относительно недавно, тем более на действующих хостингах, поэтому поддержки поздних статических связываний еще не было, и при необходимости наследования класса просто приходилось создавать синглтон-объект (да еще и немного шаблон усложнять). Если наследования не было, то и проблем с этим тоже не было. Начиная с 5.3 в принципе уже можно все (ну или может почти все) синглтоны заменять на статические классы.

Я лично не настолько фанатею от копеечной экономии на переключении контекста вызова, поэтому с синглтонов не стал переключаться на повсеместное использование статических классов.

Спустя 7 минут, 1 секунда (15.04.2012 - 11:40) caballero написал(а):
glock18

Наследовать синглтон так же глупо как и использовать вместо него статические классы. Для говносайтов без разницы а для High-load проектов очень даже существенно. Примеров много - наговнокодят а потом мемкеши прикручивают чтобы сервер не ложился.

Спустя 10 минут, 12 секунд (15.04.2012 - 11:50) m4a1fox написал(а):
glock18
Цитата
Как будет дальше, даже представить трудно. Думал, что он все хотя бы разберется в вопросе, прежде чем выкладывать что-то, но не тут то было. Ай-ай-ай, нехорошо.

О как. Тогда не стесняется и поясняем... А так можно до бесконечности гадости писать... И еще, мой вопрос выглядел так... Что будет если не используя одиночкуипонасоздавать много объектов одного класса... А не типа, как работает шаблон. Прошу, поясни мне, идиоту...

Спустя 22 минуты, 16 секунд (15.04.2012 - 12:12) glock18 написал(а):
Цитата (m4a1fox @ 15.04.2012 - 09:50)
О как. Тогда не стесняется и поясняем... А так можно до бесконечности гадости писать... И еще, мой вопрос выглядел так... Что будет если не используя одиночкуипонасоздавать много объектов одного класса... А не типа, как работает шаблон. Прошу, поясни мне, идиоту...


ну а толку его выкладывать, если никакого объяснения то даже нет. Подобных рассуждений и цитат из книжек и так немало, посмотрите хотя бы в википедию.

Что касается вашего вопроса, то здесь в теме уже раз-два прозвучал ответ. Вообще говоря вопрос несколько глупый, как по мне. Кстати говоря, пример кода приведенный вами же в начале темы отвечает на этот вопрос. Если смотреть на него открытыми глазами, конечно.

Спустя 1 минута, 46 секунд (15.04.2012 - 12:14) glock18 написал(а):
Цитата (caballero @ 15.04.2012 - 09:40)
Наследовать синглтон так же глупо как и использовать вместо него статические классы. Для говносайтов без разницы а для High-load проектов очень даже существенно. Примеров много - наговнокодят а потом мемкеши прикручивают чтобы сервер не ложился.


да, безусловно. Кажется, меня память подвела, вместо синглтона вспомнился геморрой с фабриками. Ну да суть не особо меняется, каким бы паттерн ни был - статика до 5.3 поддерживалась довольно слабенько.

Спустя 16 минут, 50 секунд (15.04.2012 - 12:31) caballero написал(а):
Цитата
вместо синглтона вспомнился геморрой с фабриками

геморрой с фабиками обычно потому что тупо имплементят паттерн. Если вместо класса фабрики использовыать обычные статические фабричные методы ( как получение инстанса у синглетона) геморроя намного меньше

Спустя 8 минут, 12 секунд (15.04.2012 - 12:39) glock18 написал(а):
Цитата (caballero @ 15.04.2012 - 10:31)
Если вместо класса фабрики использовыать обычные статические фабричные методы ( как получение инстанса у синглетона) геморроя намного меньше


потому с ним и спутал

Спустя 7 часов, 30 минут, 16 секунд (15.04.2012 - 20:09) minor написал(а):
На мой взгляд не плохо описано, продолжай в том же духи.

Спустя 40 минут, 57 секунд (15.04.2012 - 20:50) m4a1fox написал(а):
minor
Спасибо!

Спустя 1 день, 19 часов, 28 минут, 25 секунд (17.04.2012 - 16:18) SlavaFr написал(а):
1) классы пишут как правило для того чтоб ими пользоватся
задай себе вопрос сможеш ли ты его использовать если имеется 2 базы данных или имеются разные права в зависимости от user?

нет! по тому что singelton это не разрешает.

2) Если мне в люстре лампочку поменять надо, то я буду несчастлив, если мне для этого прейдется люстру с потолка снимать.
Точно так же и с классом. Зачем мне нужен такой класс которым я при наличии новой конекции не смогу пользоватсй и буду вынужден егго изменять?
Другими словами мне не в коем случае инициализированные данные которые в любой момент могутр поменятся в классе не нужны

private static $driver = 'mysql'; // db drive.
private static $host = 'localhost'; // db host
private static $dbname = 'test'; // db name
private static $dbuser = 'root'; // db user
private static $dbuserpass = ''; // db user pass


эти данные должны передоватся как параметры посредством set .
напримет setConnectData($driver,$host,$dbname,$dbuser,$dbpass);
после этого можно говорить, что мы классом пользуемся, а не переделываем его.




Спустя 2 часа, 32 минуты, 18 секунд (17.04.2012 - 18:51) minor написал(а):
Цитата
задай себе вопрос сможеш ли ты его использовать если имеется 2 базы данных или имеются разные права в зависимости от user?
нет! по тому что singelton это не разрешает.

Singelton решает поставленную перед ним задачу, часто вы работали с проектами где 2 или более бд? для нескольких бд можно сделать pool конекшенов.

Спустя 15 часов, 10 минут, 5 секунд (18.04.2012 - 10:01) SlavaFr написал(а):
Цитата (minor @ 17.04.2012 - 16:51)
часто вы работали с проектами где 2 или более бд?

последние 4 года только с такими и работаю. причем реч идет не только о разных бд, но иногда и разных серверах или одинаковых б.д. но разных юзерах с разными правами.
Цитата (minor @ 17.04.2012 - 16:51)
ля нескольких бд можно сделать pool конекшенов.

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

Спустя 10 часов, 23 минуты, 46 секунд (18.04.2012 - 20:25) minor написал(а):
Кстати кто еще будет писать гайды по патернам? если что предупреждайте про какой будете писать что бы не повторятся, возможно я решусь написать если будет свободное время в выходные.
Быстрый ответ:

 Графические смайлики |  Показывать подпись
Здесь расположена полная версия этой страницы.
Invision Power Board © 2001-2025 Invision Power Services, Inc.