我遇到了一段代码,其中调用了 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;
}
而没有将类的名称作为参数传递,如下所示:
users
现在,在官方documentation中它说:
如果fetch_style包含PDO :: FETCH_CLASSTYPE(例如PDO :: FETCH_CLASS | PDO :: FETCH_CLASSTYPE),则类的名称由第一列的值确定。
所以我不确定我究竟是什么意思,也不知道它是如何运作的。
假设我有一个记录的PDO::FETCH_CLASS
表
那么FETCH_CLASS
如何知道班级名称是什么?我可以使用类名称将列添加到我的记录中<%= f.collection_select :order_type, Order::TYPES , :to_s, :to_s, {include_blank: false}%>
将从数据库中获取类名吗?记录结构的例子将受到高度赞赏... thx
*我正在测试这个类但不是作者,所以更改类是无关紧要的
答案 0 :(得分:5)
对于 fetchAll 方法,如果未提供classname且未引发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
组合。它实际上是一种非常强大的技术,允许您跳过工厂方法中的样板开关。
答案 1 :(得分: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
个对象。