我确信这是一个非常明显的问题,并且有一个函数可以做到这一点,但我似乎找不到它。在 PHP 中,我想尽可能高效地知道我的数组中是否有重复项。我不想像
array_unique
那样删除它们,而且我也不想特别运行 array_unique
并将其与原始数组进行比较以查看它们是否相同,因为这看起来效率很低。就性能而言,“预期条件”是数组没有重复项。
我只是希望能够做类似的事情
if (no_dupes($array))
// this deals with arrays without duplicates
else
// this deals with arrays with duplicates
有什么我没有想到的明显功能吗?
如何检测 PHP 数组中的重复值?
有正确的标题,并且是一个非常相似的问题,但是如果您真正阅读了该问题,他正在寻找 array_count_values。
我知道你不是在追求
array_unique()
。然而,您不会找到一个我建议:
function array_has_dupes($array) {
// streamline per @Felix
return count($array) !== count(array_unique($array));
}
array_unique()
的第二个参数来满足您的比较需求。
如果您关心性能和微观优化,请查看以下一行:
function no_dupes(array $input_array) {
return count($input_array) === count(array_flip($input_array));
}
描述:
函数将
$input_array
中的数组元素数量与 array_flip'ed 元素进行比较。值成为键,猜猜看是什么 - 键在关联数组中必须是唯一的,这样唯一的值不会丢失,并且最终元素数量低于原始数量。
警告:
如手册中所述,数组键只能是
int
或string
类型,因此这是您必须在原始数组值中进行比较的内容,否则PHP将开始casting并产生意外结果。有关这种边缘情况故障模式的示例,请参阅 https://3v4l.org/7bRXI。
具有 1000 万条记录的数组的证明:
测试用例:
<?php
$elements = array_merge(range(1,10000000),[1]);
$time = microtime(true);
accepted_solution($elements);
echo 'Accepted solution: ', (microtime(true) - $time), 's', PHP_EOL;
$time = microtime(true);
most_voted_solution($elements);
echo 'Most voted solution: ', (microtime(true) - $time), 's', PHP_EOL;
$time = microtime(true);
this_answer_solution($elements);
echo 'This answer solution: ', (microtime(true) - $time), 's', PHP_EOL;
function accepted_solution($array){
$dupe_array = array();
foreach($array as $val){
// sorry, but I had to add below line to remove millions of notices
if(!isset($dupe_array[$val])){$dupe_array[$val]=0;}
if(++$dupe_array[$val] > 1){
return true;
}
}
return false;
}
function most_voted_solution($array) {
return count($array) !== count(array_unique($array));
}
function this_answer_solution(array $input_array) {
return count($input_array) === count(array_flip($input_array));
}
请注意,当大数组的开头附近没有唯一值时,接受的解决方案在某些情况下可能会更快。
你可以这样做:
function has_dupes($array) {
$dupe_array = array();
foreach ($array as $val) {
if (++$dupe_array[$val] > 1) {
return true;
}
}
return false;
}
$hasDuplicates = count($array) > count(array_unique($array));
如果重复,则为
true
;如果没有重复,则为 false
。
$duplicate = false;
if(count(array) != count(array_unique(array))){
$duplicate = true;
}
这是我对此的看法......经过一些基准测试,我发现这是最快的方法。
function has_duplicates( $array ) {
return count( array_keys( array_flip( $array ) ) ) !== count( $array );
}
…或者根据具体情况,这可能会稍微快一些。
function has_duplicates( $array ) {
$array = array_count_values( $array );
rsort( $array );
return $array[0] > 1;
}
要从比较中删除所有空值,您可以添加
array_diff()
if (count(array_unique(array_diff($array,array("")))) < count(array_diff($array,array(""))))
参考来自here
的@AndreKR回答我能想到的两种有效的方法:
将所有值插入某种哈希表中,并检查要插入的值是否已在其中(预计 O(n) 时间和 O(n) 空间)
对数组进行排序,然后检查相邻单元格是否相等(O(nlogn) 时间和 O(1) 或 O(n) 空间,具体取决于排序算法)
stormdrain 的解决方案可能是 O(n^2),任何涉及扫描数组以查找重复元素的解决方案也是如此
找到这个有用的解决方案
function get_duplicates( $array ) {
return array_unique( array_diff_assoc( $array, array_unique( $array ) ) );
}
之后,如果大于 0,则计数结果大于重复项,否则唯一。
保持简单,愚蠢! ;)
简单的 OR 逻辑...
function checkDuplicatesInArray($array){
$duplicates=FALSE;
foreach($array as $k=>$i){
if(!isset($value_{$i})){
$value_{$i}=TRUE;
}
else{
$duplicates|=TRUE;
}
}
return ($duplicates);
}
问候!
我正在用这个:
if(count($array)==count(array_count_values($array))){
echo("all values are unique");
}else{
echo("there's dupe values");
}
我不知道这是否是最快的,但到目前为止效果还不错
我的另一个解决方案,这个与性能提升有关
$array_count_values = array_count_values($array);
if(is_array($array_count_values) && count($array_count_values)>0)
{
foreach ($array_count_values as $key => $value)
{
if($value>1)
{
// duplicate values found here, write code to handle duplicate values
}
}
}
最短的一个
function no_dupes($array) {
return $array === array_unique($array);
}
Php 有一个函数可以计算数组中出现的次数 http://www.php.net/manual/en/function.array-count-values.php
你也可以这样做: 如果唯一,则返回 true,否则返回 false。
$nofollow = (count($modelIdArr) !== count(array_unique($modelIdArr))) ? true : false;
简单的解决方案,但速度相当快。
$elements = array_merge(range(1,10000000),[1]);
function unique_val_inArray($arr) {
$count = count($arr);
foreach ($arr as $i_1 => $value) {
for($i_2 = $i_1 + 1; $i_2 < $count; $i_2++) {
if($arr[$i_2] === $arr[$i_1]){
return false;
}
}
}
return true;
}
$time = microtime(true);
unique_val_inArray($elements);
echo 'This solution: ', (microtime(true) - $time), 's', PHP_EOL;
速度 - [0.71]!
function hasDuplicate($array){
$d = array();
foreach($array as $elements) {
if(!isset($d[$elements])){
$d[$elements] = 1;
}else{
return true;
}
}
return false;
}