Сейчас мы с вами продолжим знакомится с объектами и разберем некоторые более продвинутые вещи.

Цепочки

Реализуем класс Tag, объектом которого будет служить тег. Пользоваться классом будем так:

<?php
	$tag = new Tag('a');
	$tag->setText('ссылка')->setAttr('href', '...')->setAttr('class', 'www')->show();
?>

В результате увидим ссылку:

<a href="..." class="www">ссылка</a>

Чтобы сделать такую цепочку, нужно сделать так, чтобы каждый метод возвращал $this - в этом случае к результату метода можно примерять новый метод и так далее - и получится цепочка.

Разберите пример реализации:

<?php
	class Tag
	{
		private $name;
		private $text;
		private $attrs;

		public function __construct($name)
		{
			$this->name = $name;
		}

		public function setText($text)
		{
			$this->text = $text;
			return $this;
		}

		public function setAttr($attr, $value)
		{
			$this->attrs[$attr] = $value;
			return $this;
		}

		public function show()
		{
			$attrs = $this->attrs;
			$attrsString = $this->getAttrsString(attrs);
			
			$name = $this->name;
			$text = $this->text;

			echo "<$name $attrsString>$text</$name>";
		}

		/*
			Принимает массив,
			например ['href'=>'index.php', 'class'=>'active'],
			а возвращает строку 'href="index.php" class="active"':
		*/
		private function getAttrsString($attrs)
		{
			//реализуйте сами через foreach
		}

	}
?>

Итерируемые объекты

Публичные свойства объекта можно перебрать через цикл, смотрите пример:

<?php
	class Test
	{
		public $prop1 = 1;
		public $prop2 = 2;
		public $prop3 = 3;

		protected $prop4 = 4;
		private $prop5 = 5;
	}

	$test = new Test;
	foreach ($test as $key=>$value) {
		//Выведет: prop1-1, prop2-2, prop3-3:
		echo $key.'-'.$value.', ';
	}
?>

Обратите на этот прием внимание - он пригодится вам в дальнейшем.

Давайте сделаем так, чтобы свойствами объекта также были объекты, получится объект объектов:

<?php
	class User
	{
		public $name;

		public function __construct($name)
		{
			$this->name = $name;
		}
	}
?>
<?php
	class Users
	{
		public function __construct()
		{
			$this->user1 = new User('Коля');
			$this->user2 = new User('Вася');
			$this->user3 = new User('Петя');
		}
	}

	$users = new Users;
	foreach ($users as $user) {
		//Выведет: 'Коля', 'Вася', 'Петя':
		echo $user->name;
	}
?>

Static методы

В PHP есть специальные static методы, к которым можно обращаться, не создавая объект класса. Получается этакое ООП в функциональном стиле.

Чтобы сделать такой метод - нужно указать ключевое слово static, например так: public static function, а чтобы обратиться к нему - нужно написать имя класса, потом два двоеточия и метод (объект класса создавать не надо - сразу обращаемся).

Кроме того для static методов (и свойств тоже) вместо $this-> следует использовать self::.

Смотрите пример:

<?php
	class Db
	{
		public static function save()
		{
			...;
		}

	}

	Db::save();
?>

Можно также делать и static свойство. В этом случае это свойство будет общим для всех объектов этого класса - если записать в него что-то в одном объекте, то это свойство поменяется во всех объектах этого класса.

Давайте сделаем класс, который считает количество своих объектов в static свойстве $count:

<?php
	class User
	{
		private static $count = 0;
		public $name;

		public function __construct($name)
		{
			//При создании объекта счетчик увеличивается:
			self::$count++;
			$this->name = $name;
		}

		public static function getCounter()
		{
			//Выводим значение счетчика:
			return self::$count;
		}

	}

	$user1 = new User();
	echo User::getCounter(); //выведет 1

	$user2 = new User();
	echo User::getCounter(); //выведет 2
?>

Пространства имен

Автозагрузка классов

Магические методы

Методы PHP, начинающиеся с двойного подчеркивания __, называются магическим. Магия таких методов состоит в том, что они могут вызываться при совершении какого-то действия автоматически.

Один из магических методов - __construct - уже вам знаком.

Есть также магические методы-перехватчики __get, __set, __isset, __unset, __call. Они называются перехватчиками, так как перехватывают обращение к недоступным или несуществующим членам класса.

О них будет чуть позже, пока см. статью true-coder.ru/oop-v-php/oop-v-php-magicheskie-metody-metody-perexvatchiki.html.