使用 Laravel 的查询构建器返回完整的重复行
Returning full duplicate rows using Laravel's query builder
我正在 return 我的 table 中查找有关重复记录的完整信息。
我目前使用的是:
DB::table($entity['table'])
->select('*')
->groupBy($entity['columns'])
->havingRaw('COUNT(*) > 1')
->get();
太棒了,它 return 是重复的记录,但是,这只是 return 的记录之一,我需要 return 所有的重复记录,以便我可以问候用户可以选择删除或保留哪一个。
我如何修改上述查询来完成它?
您需要在 $entity['columns'] 中的列上重新加入 $entity['table'] 中的 table 以获取重复项。
此外,即使您使用 mysql,select('*') 也不是一个好主意。这违反了 sql 标准,并且只有在以某种方式配置时才能在 mysql 中工作。如果配置更改或您将应用程序迁移到 sql 模式下具有不同配置的 mysql 服务器,您的查询将失败。
我也会在 select 列表中使用 $entity['columns']。
在 sql 中,查询应如下所示:
select table.* from table inner join
(select field1, field2 from table t
group by field1, field2
having count(*)>1) t1
on table.field1=t1.field1 and table.field2=t1.field2
加入相同的 table 将允许您检索重复的记录而不仅仅是获取它的单一版本(由您的问题中的 groupBy 引起)
$entity['columns'] = ['username', 'surname'];
$groupBy = implode(',', $entity['columns']);
$subQuery = DB::table('list')
->select('*')
->groupBy($groupBy)
->havingRaw('(count(id) > 1))');
$result = DB::table('list')
->select('*')
->join(
DB::raw("({$subQuery->toSql()}) dup"), function($join) use ($entity) {
foreach ($entity['columns'] as $column) {
$join->on('list.'.$column, '=', 'dup.'.$column);
}
})
->toSql();
// or ->get(); obviously
dd($result);
您可以通过使用 whereIn 和一个函数来查询您正在使用的同一个 table 来完成此操作。
假设您有一个场景,您想要在用户 table.
中查找包含相同姓氏的重复记录
数据库Table - 用户
--- user_id --- first_name --- last_name --- email ---
1 Dan Smith dan@test.com
2 Jim Jones jim@test.com
3 Amy Grant amy@test.com
4 Bob Brown bob@test.com
5 Sue Davis sue@test.com
6 Leo Grant leo@test.com
7 Ann Grant ann@test.com
那么就可以使用下面的代码了;
$duplicates = DB::table('user')
->select('user_id', 'last_name')
->whereIn('user_id', function ($q){
$q->select('user_id')
->from('user')
->groupBy('last_name')
->havingRaw('COUNT(*) > 1');
})->get();
return以下内容;
--- user_id --- last_name
3 Grant
6 Grant
7 Grant
我正在 return 我的 table 中查找有关重复记录的完整信息。
我目前使用的是:
DB::table($entity['table'])
->select('*')
->groupBy($entity['columns'])
->havingRaw('COUNT(*) > 1')
->get();
太棒了,它 return 是重复的记录,但是,这只是 return 的记录之一,我需要 return 所有的重复记录,以便我可以问候用户可以选择删除或保留哪一个。
我如何修改上述查询来完成它?
您需要在 $entity['columns'] 中的列上重新加入 $entity['table'] 中的 table 以获取重复项。
此外,即使您使用 mysql,select('*') 也不是一个好主意。这违反了 sql 标准,并且只有在以某种方式配置时才能在 mysql 中工作。如果配置更改或您将应用程序迁移到 sql 模式下具有不同配置的 mysql 服务器,您的查询将失败。
我也会在 select 列表中使用 $entity['columns']。
在 sql 中,查询应如下所示:
select table.* from table inner join
(select field1, field2 from table t
group by field1, field2
having count(*)>1) t1
on table.field1=t1.field1 and table.field2=t1.field2
加入相同的 table 将允许您检索重复的记录而不仅仅是获取它的单一版本(由您的问题中的 groupBy 引起)
$entity['columns'] = ['username', 'surname'];
$groupBy = implode(',', $entity['columns']);
$subQuery = DB::table('list')
->select('*')
->groupBy($groupBy)
->havingRaw('(count(id) > 1))');
$result = DB::table('list')
->select('*')
->join(
DB::raw("({$subQuery->toSql()}) dup"), function($join) use ($entity) {
foreach ($entity['columns'] as $column) {
$join->on('list.'.$column, '=', 'dup.'.$column);
}
})
->toSql();
// or ->get(); obviously
dd($result);
您可以通过使用 whereIn 和一个函数来查询您正在使用的同一个 table 来完成此操作。
假设您有一个场景,您想要在用户 table.
中查找包含相同姓氏的重复记录数据库Table - 用户
--- user_id --- first_name --- last_name --- email --- 1 Dan Smith dan@test.com 2 Jim Jones jim@test.com 3 Amy Grant amy@test.com 4 Bob Brown bob@test.com 5 Sue Davis sue@test.com 6 Leo Grant leo@test.com 7 Ann Grant ann@test.com
那么就可以使用下面的代码了;
$duplicates = DB::table('user')
->select('user_id', 'last_name')
->whereIn('user_id', function ($q){
$q->select('user_id')
->from('user')
->groupBy('last_name')
->havingRaw('COUNT(*) > 1');
})->get();
return以下内容;
--- user_id --- last_name 3 Grant 6 Grant 7 Grant