PDO – FETCH_CLASS – передать результаты в конструктор в качестве параметров

Есть ли способ передать результаты PDO в качестве параметров конструктора? Скажем, у меня есть следующий класс:

class Test { private $value1; private $value2; function __construct($val1, $val2) { $this->value1 = $val1; $this->value2 = $val2; } } 

Затем, используя драйвер PDO, я выбираю некоторые данные из БД, скажем:

 SELECT price, quantity FROM stock $results = $query->fetchAll(PDO::FETCH_CLASS|PDO::FETCH_PROPS_LATE, "Test"); 

Прямо сейчас, PDO пропускает эти значения непосредственно к полям класса и обходит конструктор.

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

Solutions Collecting From Web of "PDO – FETCH_CLASS – передать результаты в конструктор в качестве параметров"

[Я отредактировал этот ответ, так как мой предыдущий ответ больше не точен.]

FETCH_CLASS извлекает частные свойства. Пожалуйста, обратитесь к этому ответу .

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

Результаты запроса могут быть привязаны к вашим свойствам объекта напрямую с помощью PDO::FETCH_CLASS

нам также нужен конструктор, который может перезаписать значения из PDO, если это необходимо, поэтому удалите PDO::FETCH_PROPS_LATE из fetch .

 function __construct($val1=null, $val2=null) { // now the constructor is called after the fetch // if you pass values to it, they will be assigned if ($val1!==null) $this->price = $val1; if ($val2!==null) $this->quantity = $val2; } 

у нас есть два способа создания объекта

PDO

 $stmt = $db->prepare('SELECT price, quantity FROM stock'); $stmt->setFetchMode(PDO::FETCH_CLASS,'Test'); $result = $stmt->fetch(); 

новый

 $result = new Test(25,100); 

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

 function __construct($val1=null, $val2=null) { if ($val1!==null) $this->price = $val1; if ($val2!==null) $this->quantity = $val2; $this->formattedPrice = number_format($this->price,'2'); } 

Единственный способ, которым я понял, – использовать константу FETCH_FUNC и предоставить функцию для создания объекта через конструктор.

 function rowMapper( $price, $quantity) { return new Test( $price, $quantity); } $results = $query->fetchAll( PDO::FETCH_FUNC, "rowMapper"); 

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

В вашем случае вы можете передать их следующим образом:

 $results = $query->fetchAll(PDO::FETCH_CLASS|PDO::FETCH_PROPS_LATE, "Test", array('val1', 'val1')); 

Читайте о третьем параметре для fetchAll() здесь .

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

 class User { private $id; public $name; public $isMinor; // make sure parameters are in the same order as the mysql result public static function buildFromPdo($id, $age, $name) { $user = new self; $user->id = $id; $user->name = $name; $user->isMinor = $age < 18; return $user; } public function getId() { return $this->id; } } $stmt = $db->prepare('SELECT id, age, name FROM users'); $stmt->execute(); $result = $stmt->fetchAll(PDO::FETCH_FUNC, "User::buildFromPdo"); 

«$ result» будет массивом объектов User.