Upload
eatdog
View
151
Download
2
Embed Size (px)
Citation preview
Почему ООП?
• Это удобно
• Это расширяемо
• Адекватная модель мира
• Позволяет строить асбтракции
• Мне так сказали
8
Пожалуйста, не делайте так:
use Spatie\Regex\Regex;
// Using `match`
Regex::match('/a/', 'abc'); // `MatchResult` object
Regex::match('/a/', 'abc')->hasMatch(); // true
Regex::match('/a/', 'abc')->result(); // 'a'
01.
02.
03.
04.
05.
06.
13
Вместо:
Regex::match('/a/', 'abc'); // `MatchResult` objectRegex::match('/a/', 'abc')->hasMatch(); // trueRegex::match('/a/', 'abc')->result(); // 'a'
лучше:
$pattern = new Regex('/a/');$matchingResult = $pattern->match('abc'); // `MatchResult` object$matchingResult->hasMatch(); // true$matchingResult->result(); // 'a'
01.02.03.
01.02.03.04.
14
Вместо:
Assertion::nullOrMax(null, 42); // successAssertion::nullOrMax(1, 42); // successAssertion::nullOrMax(1337, 42); // exception
лучше:
// since PHP 5.6Assertion\nullOrMax(null, 42); // successAssertion\nullOrMax(1, 42); // successAssertion\nullOrMax(1337, 42); // exception
01.02.03.
01.02.03.04.
15
interface Container {
public function drop();
}
class Glass implements Container {
public function drop() { /* well, crash */ }
}
class Cup implements Container {
public function drop() { /* well, crash, and throw the handle out */ }
}
class Cat {
public function dropContainer(Container $container) {
$container->drop();
}
}
01.
02.
03.
04.
05.
06.
07.
08.
09.
10.
11.
12.
13.
14.
29
$cat = new Cat();
$cat->dropContainer(new Glass());
$cat->dropContainer(new Cup());
$cat->runAway();
01.
02.
03.
04.
30
class ContainerCollection implements Iterator { public function current() : Container { /* ... */ }; // ...} $containersOnTable = new ContainerCollection(); // Your mom fills the collection here:$eventManager->dispatch('serve_table', $containers); array_walk($containersOnTable, function(Container $container) use ($cat) { $cat->dropContainer($container); });
01.02.03.04.05.06.07.08.09.10.11.12.13.14.15.
31
Инкапсуляция помогает скрыть реализацию за абстракицей.
Наследование помогает строить абстракции.
Полиморфизм помогает писать код на основе абстракций.
32
class SearchEngine { public function indexProduct(Product $product) { $this->productIndex->add($product); $indexIsUpToDate = $this->productIndex->isUpToDate(); //.. }}
01.02.03.04.05.06.07.
35
Метод-команда
• принимает запрос на изменение состояния объекта,
• ничего не возвращает (void),
• выполняется успешно, либо бросает исключение.
37
Метод-запрос
• принимает запрос на получение информации,
• возвращает значение указанного типа,
• если это невозможно, возвращает NULL ,
• или бросает исключение,
• никогда не меняет наблюдаемое состояние объекта.
*
*
38
class Person { private $firstName, $lastName, $gender, $email; // __constructor() // getters // setters} $person = new Person('Sheldon', 'Cooper', 'M', '[email protected]');render($person);
01.02.03.04.05.06.07.08.09.
42
class Person { private $firstName, $lastName, $gender, $email; // __constructor() // getters // setters} $person = new Person('Sheldon', 'Cooper', 'M', '[email protected]'); $person->setFirstName('Penny');$person->setGender('F'); render($person);
01.02.03.04.05.06.07.08.09.10.11.12.13.
44
class Person { private $firstName, $lastName, $email, $gender; public function rename(NameChangingRequest $request) { // change first/last/... names depending on request // throw exception if name is not male, for instance } public function changeGender(GenderChangingRequest $request) { // A request which contains also the new name, // maybe the reason or whatever is needed. }} $person->changeGender(new GenderChangingRequest('M', 'New Name'));
01.02.03.04.05.06.07.08.09.10.11.12.13.14.15.
47
class Product { public function reduceQuantity($deltaQuantity) { $this->quantity -= $deltaQuantity; } public function verifyStockAvailability() { if ($this->quantity == 0) { $this->removeFromStock(); } }} $product->reduceQuantity($orderedQuantity);$product->verifyStockAvailability();
01.02.03.04.05.06.07.08.09.10.11.12.13.
49
class Product { private function reduceQuantity($deltaQuantity) { /*...*/ } private function verifyStockAvailability() { /*...*/ } public function takeFromStock($quantity) { try { $this->reduceQuantity($orderedQuantity); $this->verifyStockAvailability(); } catch() { // ... } }} $product->takeFromStock($orderedQuantity);
01.02.03.04.05.06.07.08.09.10.11.12.13.14.15.
50
function getProductUrl($product) {
return '/'
. str_replace(' ', '-', strtolower($product));
}
01.
02.
03.
04.
52
$product = 'Ski Boots'; // product name
$product = 456; // product id
$product = [ // product data
'id' => 456,
'name' => 'Ski Boots'
];
01.
02.
03.
04.
05.
06.
53
Name things by their real value
• $product — object
• $productName — string
• $productId — integer / hash
• $productData — array / structure
54
$person->addContactInformation(
new EmailAddress('[email protected]')
);
$person->addContactInformation(
new LinkedInProfileUrl('@max.gopey')
);
$this->redirect(new Url('https://stackoverflow.com'));
01.
02.
03.
04.
05.
06.
07.
56
Интернет-аптека для ветеринаров.
Можно покупать товар:
• для клиники (clinic),
• для клиента (pet owner).
От этого зависит процесс заказа. Например, при заказе для
клиента можно оформить доставку в клинику или на дом.
59
class Cgi_Nda_Model_Order_Mode
{
const ORDER_MODE_CLINIC = 1;
const ORDER_MODE_PET_OWNER = 2;
}
01.
02.
03.
04.
05.
60
class Cgi_Nda_Model_Session
{
public function getOrderMode() : int {
return $this->getSessionValue('order_mode');
}
}
01.
02.
03.
04.
05.
06.
61
class Cgi_Nda_Block_Order_Mode_Info{ public function getOrderMode () { $orderMode = $this->_getSession()->getOrderMode(); if ($orderMode) { if ($orderMode == Cgi_Nda_Model_Order_Mode::ORDER_MODE_PET_OWNER) { return 'For pet owner' ; } elseif ($orderMode == Cgi_Nda_Model_Order_Mode::ORDER_MODE_CLINIC) { return 'For clinic' ; } else { return false; } } else { return false; } } public function isSeparateShippingAddressAllowed () { $orderMode = $this->_getSession()->getOrderMode(); return $orderMode && $orderMode == Cgi_Nda_Model_Order_Mode::ORDER_MODE_PET_OWNER }}
01.02.03.04.05.06.07.08.09.10.11.12.13.14.15.16.17.18.19.20.21.22.23.24.
62
interface Cgi_Nda_Model_Order_Mode_Interface{ public function getCode() : int; public function getTitle() : string; public function isSeparateShippingAddressAllowed() : bool;}
01.02.03.04.05.06.07.08.
63
class Cgi_Nda_Model_Order_Mode_Clinic implements Cgi_Nda_Model_Order_Mode_Interface{ public function getCode() : int { return 1; } public function getTitle() : string { return 'For Clinic'; } public function isSeparateShippingAddressAllowed() : bool { return false; }} class Cgi_Nda_Model_Order_Mode_PetOwner implements Cgi_Nda_Model_Order_Mode_Interface{ public function getCode() : int { return 2; } public function getTitle() : string { return 'For Pet Owner'; } public function isSeparateShippingAddressAllowed() : bool { return true; }}
01.02.03.04.05.06.07.08.09.10.11.12.13.14.15.16.17.18.19.20.21.22.23.24.25.
64
class Cgi_Nda_Model_Session
{
public function getOrderMode()
: Cgi_Nda_Model_Order_Mode_Interface {
return $this->getSessionValue('order_mode');
}
}
01.
02.
03.
04.
05.
06.
07.
65
class Cgi_Nda_Block_Order_Mode_Info{ private $orderMode; public function __construct( Cgi_Nda_Model_Order_Mode_Interface $orderMode ) { $this->orderMode = $orderMode; } public function getOrderModeTitle() { return $this->orderMode->getTitle(); } public function isSeparateShippingAddressAllowed() { return $this->orderMode->isSeparateShippingAddressAllowed(); }}
01.02.03.04.05.06.07.08.09.10.11.12.13.14.15.16.17.18.
66