[英]Overriding fetch() for PDO when fetching using foreach
I have extended PDOStatement
and modified the fetch()
method to typecast values of the types timestamp and arrays, in PostgreSQL, to DateTime and native array. 我已经扩展了PDOStatement
并修改了fetch()
方法,以便在PostgreSQL中将类型timestamp和数组的类型转换为DateTime和native数组。 This works as intended but I can't override the behaviour when using the statement in a foreach. 这按预期工作,但在foreach中使用语句时我无法覆盖该行为。
I have solved this by returning rows into an object implementing ArrayAccess, IteratorAggregate and Countable. 我通过将行返回到实现ArrayAccess,IteratorAggregate和Countable的对象来解决这个问题。 However I'm not satisfied with that solution and just want a pure array back. 但是我对这个解决方案并不满意,只想要一个纯粹的阵列。
Example: 例:
class ExtendedStatement extends PDOStatement { protected function __construct() { $this->setFetchMode(PDO::FETCH_ASSOC); } public function fetch( $fetch_style = PDO::FETCH_ASSOC, $cursor_orientation = PDO::FETCH_ORI_NEXT, $cursor_offset = 0) { $r = parent::fetch($fetch_style, $cursor_orientation, $cursor_offset); if (is_array($r)) { $r["extradata"] = TRUE; } return $r; } } $db = new PDO("sqlite::memory:"); $db->setAttribute( PDO::ATTR_STATEMENT_CLASS, array("ExtendedStatement", array($db))); $db->exec("CREATE TABLE example(id INTEGER PRIMARY KEY, name VARCHAR)"); $db->exec("INSERT INTO example(name) VALUES('test')"); // This is what is does $s = $db->prepare("SELECT * FROM example"); $s->execute(); foreach ($s as $r) { var_dump($r); } $s->closeCursor(); // This is how I want it to be $s = $db->prepare("SELECT * FROM example"); $s->execute(); while ($r = $s->fetch()) { var_dump($r); } $s->closeCursor(); // This is how I want it to be $s = $db->prepare("SELECT * FROM example"); $s->execute(); var_dump($s->fetch()); $s->closeCursor();
Output: 输出:
array(2) { ["id"]=> string(1) "1" ["name"]=> string(4) "test" } array(3) { ["id"]=> string(1) "1" ["name"]=> string(4) "test" ["extradata"]=> bool(true) } array(3) { ["id"]=> string(1) "1" ["name"]=> string(4) "test" ["extradata"]=> bool(true) }
The PDOStatement
class implements the built-in internals-only Traversable
interface. PDOStatement
类实现了内置的仅内部Traversable
接口。 The iterator that it implements bypasses the public PDOStatement::fetch()
method. 它实现的迭代器绕过公共PDOStatement::fetch()
方法。
I use something like this: 我使用这样的东西:
$db->setAttribute(PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false);
$sql = 'select * from table';
$stmt = $db->prepare($sql);
$stmt->execute();
while($row = $stmt->fetch(PDO::FETCH_ASSOC, PDO::FETCH_ORI_NEXT))
{
// do stuff
}
So the only thing you have to do is set some options :) 所以你唯一要做的就是设置一些选项:)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.