如何迭代 Yii CActiveDataProvider 对象?
Posted
技术标签:
【中文标题】如何迭代 Yii CActiveDataProvider 对象?【英文标题】:How to iterate over Yii CActiveDataProvider object? 【发布时间】:2012-08-23 14:25:28 【问题描述】:如何迭代 dataprovider 对象?我想访问返回的每一行的“名称”字段并构建一个列表。你能帮忙吗?
表/模型categories
的表结构
CREATE TABLE IF NOT EXISTS `categories` (
`idCategory` int(10) unsigned NOT NULL AUTO_INCREMENT,
`name` varchar(64) NOT NULL,
PRIMARY KEY (`idCategory`) USING BTREE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=55 ;
*我的控制器类别中的函数*
$names = array();
public function returnCategoryNames()
$dataProvider= new CActiveDataProvider('Categories');
$dataProvider->setPagination(false);
$count = $dataProvider->totalItemCount();
for($i = 0; $i < $count; $i++)
// this is where I am lost...
$myname = $dataProvider->data[$i]->name;
array_push($names, $myname);
return $names;
【问题讨论】:
【参考方案1】:在 Yii2 中这也发生了变化:
$searchModel = new ModelSearch();
$dataProvider = $searchModel->search(Yii::$app->request->queryParams);
foreach($dataProvider->getModels() as $record)
echo $record->id . '<br>';
exit();
参考:getModels()
【讨论】:
【参考方案2】:使用@ben-rowe 的解决方案,您可以一次查询所有行。您可能会遇到内存问题。
使用以下解决方案,您将从十乘十获取类别(默认 CPagination.pageSize
值):
$dataProvider = new CActiveDataProvider('Categories', array(
'pagination' => array(
'validateCurrentPage' => false
),
));
$pagination = $dataProvider->pagination;
while ($categories = $dataProvider->getData(true))
foreach ($categories as $category)
//...
$pagination->currentPage++;
【讨论】:
感谢这个解决方案!【参考方案3】:如果您需要大量数据收集并且担心内存使用情况,请执行以下操作:
$dataProvider = new CActiveDataProvider('Categories');
$iterator = new CDataProviderIterator($dataProvider);
foreach($iterator as $category)
print_r($category);
CDataProviderIterator 允许对大型数据集进行迭代,而无需将整个数据集保存在内存中。
一些性能测试
测试时间(秒) 内存(字节) CDbDataReader 4.9158580303192 28339952 CActiveRecord::findAll() 5.8891110420227 321388376 CDataProviderIterator 6.101970911026 31170504【讨论】:
CDataProvider 仍然会调用 findAll(),它只是允许您指定要通过分页进行实际 sql 查询的次数。 CDbDataReader 只进行 1 次 sql 调用并以内存高效的方式迭代结果。 CDataProviderIterator 与 CDataProvider 不同【参考方案4】:试试这个:
public function returnCategoryNames()
$dataProvider= new CActiveDataProvider('Categories');
$dataProvider->setPagination(false);
//$count = $dataProvider->totalItemCount();
$names = array();
foreach($dataProvider->getData() as $record)
$names[] = $record->name;
return array_unique($names);
但是您不需要使用数据提供者,而只需使用模型
foreach(Categories::model()->findAll() as $record)
【讨论】:
我真的很喜欢你给的第二个选项(Categories::model())。有没有办法用这个选项做 ORDER BY ?还是要求太多了 easy:Categories::model()->findAll(array('order' => 'name'));
,您可以在以下位置找到有关 find() 命令的详细信息:yiiframework.com/doc/api/1.1/CActiveRecord#findAll-detail以上是关于如何迭代 Yii CActiveDataProvider 对象?的主要内容,如果未能解决你的问题,请参考以下文章