PDO::FETCH_CLASS 不传递类名作为参数
Posted
技术标签:
【中文标题】PDO::FETCH_CLASS 不传递类名作为参数【英文标题】:PDO::FETCH_CLASS without passing class name as a parameter 【发布时间】:2015-09-08 13:20:55 【问题描述】:我遇到了一段代码,其中调用 PDO::FETCH_CLASS
时没有将类的名称作为参数传递,如下所示:
function getUsers()
$DBH = $this->getDbh();
$query = "SELECT * FROM users";
try
$STH = $DBH->query($query);
$users = $STH->fetchAll(PDO::FETCH_CLASS);
catch(PDOException $e)
return $users;
现在,在官方documentation 中写道:
如果 fetch_style 包含 PDO::FETCH_CLASSTYPE(例如 PDO::FETCH_CLASS | PDO::FETCH_CLASSTYPE),则类的名称由第一列的值确定。
所以我不确定我是否完全理解它们的意思以及它是如何工作的。
假设我有一个记录的users
表
那么PDO::FETCH_CLASS
怎么知道类名是什么?我可以以FETCH_CLASS
从数据库中获取类名的方式将列添加到我的记录中吗?记录结构的例子将受到高度赞赏...thx
*我正在测试这个类但不是作者所以改变类是无关紧要的
【问题讨论】:
我有一种奇怪的感觉,这是一个错字,他们的意思是“表名”——但我是基于零事实证据:) 其实它只是返回一个\stdClass
实例,比如PDO::FETCH_OBJ
。
【参考方案1】:
对于 fetchAll 方法,如果未提供类名且未引发 PDO::FETCH_CLASSTYPE
标志,则返回 stdClass
对象(就像 PDO::FETCH_OBJ
一样)。这就是发生的事情(lxr):
1436 switch(how & ~PDO_FETCH_FLAGS)
1437 case PDO_FETCH_CLASS:
1438 switch(ZEND_NUM_ARGS())
1439 case 0:
1440 case 1:
1441 stmt->fetch.cls.ce = zend_standard_class_def;
1442 break
然后,在do_fetch
中,由于没有提供类名,因此该值保持不变。这是有道理的,因为stdClass
有时被认为是某种匿名类。 )
这解释了您必须处理的代码; @eggyal 的回答解释了如何使用 PDO::FETCH_CLASS || PDO::FETCH_CLASSTYPE
组合。它实际上是一种非常强大的技术,可以让您跳过工厂方法中的样板开关。
【讨论】:
引用源代码的答案的无可争辩的证明......喜欢:)【参考方案2】:我不确定我完全理解它们的意思或它是如何工作的
他们的意思是,而不是
$STH = $DBH->query("SELECT * FROM users");
$users = $STH->fetchAll(PDO::FETCH_CLASS, 'UserClass');
您可以执行以下操作:
$STH = $DBH->query("SELECT 'UserClass', users.* FROM users");
$users = $STH->fetchAll(PDO::FETCH_CLASS | PDO::FETCH_CLASSTYPE);
但是,这并不是特别有用:为什么将类名硬编码到 SQL 中只是为了让 mysql 在每条记录中返回它,并且 PDO 在实例化结果对象时解析每个字段(即每条记录)?最好将类名指定为fetchAll()
的第二个参数,如上面的第一个示例所示。
我应该在我的记录中添加带有类名的列吗?
嗯,确实,也可以这样做——这是对这个功能更有用的用途:它使每个结果对象的类都依赖于记录本身,这在某些情况下可能很有用(即在并非结果集中的所有记录都具有相同的“类型”——例如:也许有些记录应该实例化 Employee
对象,而其他记录应该实例化 Customer
对象)。
【讨论】:
这不是我的反对意见,但这个SELECT 'UserClass'
应该可能是标记`
或根本没有。可能是他们投反对票并闭嘴的原因。
'SELECT 'UserClass', users.* FROM users'
不是有效的 php,会产生致命错误。
您在描述 FETCH_CLASS 的可能用例时是正确的 || FETCH_CLASSTYPE fetch
组合,因此我 +1。 )
@eggyal 来自我的评论 #1 仍然适用。事实上,我什至赞成 ;-)
@Fred-ii-:我将 PHP 字符串从单引号改为双引号 — 所以 'UserClass'
现在是 SQL 字符串文字,它应该是(而不是一些错误的 PHP 标识符,因为它是)。以上是关于PDO::FETCH_CLASS 不传递类名作为参数的主要内容,如果未能解决你的问题,请参考以下文章