我有 2 个表格,其中填充了值:
`users`
id | name | account_id | card_id
`cards`
id | name | account_id
现在我需要从 users
.card_id
列获取所有值,从 cards
查找所有记录,其中 cards
.id
= users
.card_id
,然后从表 cards
的这些记录中获取 account_id 的值
并使用这些值更新 users
.account_id
。您能告诉我使用 Yii2 和 Active Record 实现此目的的正确方法吗?
我的代码:
class CodeController
{
public function actionGo()
{
$cardsIdsFromUsers = Users::find()
->select('card_id')
->column();
$accountsFromCards = Cards::find()
->where(['id' => $cardsIdsFromUsers])
->all();
foreach($accountsFromCards as $account){
$user = Users::find()
->where(['card_id' => $account->id])
->one();
$user->account_id = $account->account_id;
$user->update();
}
}
}
这段代码可以工作,但是两个表中都有 20k 行,并且代码运行速度非常慢。另外,我知道我的代码远非最佳,所以请提供如何使其正确的建议。
最佳答案
您可以使用 \yii\db\Connection
的 createCommand()
方法来创建两个表的更新,如下所示
$command = \Yii::$app->db->createCommand(
'UPDATE users, cards SET users.account_id = cards.account_id WHERE cards.id = users.card_id'
);
$command->execute();
只有当这两个表之间的关系为 1:1 时,此方法才能正常工作。
但是您应该问自己两个问题:
1) 您真的需要在两个表中保存 account_id 吗?数据冗余通常是一个坏主意,因为它会引发一些一致性问题。
2) 这两个表中的一张卡 ID 的 account_id 可以不同吗?如果帐户 ID 应始终相同,那么您应该考虑使用 triggers 。当一个表中的 account_id 更改时,触发器会更新另一个表,而不是偶尔更新所有表。
更新:在下面的评论中已经澄清,表位于同一 MySQL 服务器上的不同数据库中,可由单个数据库用户访问。
如果 mysql 用户可以访问这两个表,则只需在表名前加上数据库名称前缀即可对不同数据库中的两个表进行 UPDATE 查询。假设 Yii::$app->db
中的连接设置为可以访问两个数据库的用户,代码将如下所示:
$command = \Yii::$app->db->createCommand(
'UPDATE db1.users, db2.cards SET users.account_id = cards.account_id WHERE cards.id = users.card_id'
);
$command->execute();
注意:SQL命令中的db1和db2应替换为包含表的数据库的实际名称。
关于php - 如何使用 Yii2 ActiveRecord 更新多行?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58719460/