Получить ключи для повторяющихся значений в массиве

если мои массивы

Array ( [0] => 2011-06-21 [1] => 2011-06-22 [2] => 2011-06-22 [3] => 2011-06-23 [4] => 2011-06-23 [5] => 2011-06-24 [6] => 2011-06-24 [7] => 2011-06-25 [8] => 2011-06-25 [9] => 2011-06-26 [10] => 2011-06-26 [11] => 2011-06-27 [12] => 2011-06-27 [13] => 2011-06- 28 [14] => 2011-06-29 [15] => 2011-06-29 [16] => 2011-06-30 [17] => 2011-06-30 [18] => 2011-07-01 [19] => 2011-07-01 [20] => 2011-07-02 [21] => 2011-07-02 [22] => 2011-07-03 [23] => 2011-07-03 [24] => 2011-07-04 [25] => 2011-07-04 [26] => 2011-07-05 [27] => 2011- 07-05 [28] => 2011-07-06 [29] => 2011-07-06 [30] => 2011-07-07 [31] => 2011-07-07 ) 
  1. Теперь, как я могу отображать ключи с повторяющимися значениями? например. Здесь функция НЕ должна возвращаться ([0], [13]), так как нет дубликатов со значениями.
  2. Как найти ключ для значения, например «2011-06-29», он должен вернуться [15], [16]

 function get_keys_for_duplicate_values($my_arr, $clean = false) { if ($clean) { return array_unique($my_arr); } $dups = $new_arr = array(); foreach ($my_arr as $key => $val) { if (!isset($new_arr[$val])) { $new_arr[$val] = $key; } else { if (isset($dups[$val])) { $dups[$val][] = $key; } else { $dups[$val] = array($key); // Comment out the previous line, and uncomment the following line to // include the initial key in the dups array. // $dups[$val] = array($new_arr[$val], $key); } } } return $dups; } 

очевидно, имя функции немного длиннее;)

Теперь $ dups будет содержать многомерный массив с двойным значением, содержащий каждый ключ, который является дубликатом, и если вы отправите «true» в качестве второго аргумента, он вернет исходный массив без повторяющихся значений.

Альтернативно вы можете передать исходный массив в качестве ссылки, и он будет соответствующим образом регулировать его, возвращая ваш дублированный массив

Сначала я отвечу на второй вопрос. Вы хотите использовать array_keys с указанным «search_value».

 $keys = array_keys($array, "2011-06-29") 

В приведенном ниже примере, $duplicates будет содержать значения дублирования, в то время как $result будет содержать те, которые не дублируются. Чтобы получить ключи, просто используйте array_keys .

 <?php $array = array( 'a', 'a', 'b', 'c', 'd' ); // Unique values $unique = array_unique($array); // Duplicates $duplicates = array_diff_assoc($array, $unique); // Unique values $result = array_diff($unique, $duplicates); // Get the unique keys $unique_keys = array_keys($result); // Get duplicate keys $duplicate_keys = array_keys(array_intersect($array, $duplicates)); 

Результат:

 // $duplicates Array ( [1] => a ) // $result Array ( [2] => b [3] => c [4] => d ) // $unique_keys Array ( [0] => 2 [1] => 3 [2] => 4 ) // $duplicate_keys Array ( [0] => 0 [1] => 1 ) 
 $array = array(0 => "1", 1 => "1", 2 => "2", 3 => "3"); $count = array(); foreach($array as $key => $value) { if(!isset($count[$value])) { $count[$value] = 0; } $count[$value]++; } $result = array_filter($count, function($value) { return $value > 1; }); $result = array_keys($result); var_dump($result); 

Вывод

 array(1) { [0]=> int(1) } 

вот код чувак

  $your_array = array(0 => '2011-06-21', 1 => '2011-06-22', 2 => '2011-06-22', 3 => '2011-06-23', 4 => '2011-06-23', 5 => '2011-06-24', 6 => '2011-06-24', 7 => '2011-06-25', 8 => '2011-06-25', 9 => '2011-06-26', 10 => '2011-06-26', 11 => '2011-06-27', 12 => '2011-06-27', 13 => '2011-06- 28', 14 => '2011-06-29', 15 => '2011-06-29', 16 => '2011-06-30', 17 => '2011-06-30', 18 => '2011-07-01', 19 => '2011-07-01', 20 => '2011-07-02', 21 => '2011-07-02', 22 => '2011-07-03', 23 => '2011-07-03', 24 => '2011-07-04', 25 => '2011-07-04', 26 => '2011-07-05', 27 => '2011- 07-05', 28 => '2011-07-06', 29 => '2011-07-06', 30 => '2011-07-07', 31 => '2011-07-07'); $keys_of_duplicated = array(); $array_keys = array(); foreach($your_array as $key => $value) { //- get the keys of the actual value $array_keys = array_keys($your_array, $value); //- if there is more then one key collected we register it if(count($array_keys) > 1) { //- foreach key that have the same value we check if i'ts already registered foreach($array_keys as $key_registered) { //- if not registered we register it if(!in_array($key_registered, $keys_of_duplicated)) { $keys_of_duplicated[] = $key_registered; } } } } var_dump($keys_of_duplicated); 

$ keys_of_duplicated – теперь массив, содержащий ключи дублированных массивов;) bye

У меня была аналогичная проблема с вопросом № 1 от ОП. Все, что мне было нужно, это ключи для повторяющихся значений в моем исходном массиве. Вот что я придумал:

 $array = array('yellow', 'red', 'green', 'brown', 'red', 'brown'); $counts = array_count_values($array); $filtered = array_filter($counts, function($value) { return $value != 1; }); $result = array_keys(array_intersect($array, array_keys($filtered))); 

И для выхода:

 print_r($result); Array ( [0] => 1 [1] => 3 [2] => 4 [3] => 5 ) 
 function getDuplicateValueKeys($my_arr, $clean = false) { if ($clean) { return array_unique($my_arr); } $dups = array(); $new_arr = array(); $dup_vals = array(); foreach ($my_arr as $key => $value) { if (!isset($new_arr[$value])) { $new_arr[$value] = $key; } else { array_push($dup_vals,$value); } } foreach ($my_arr as $key => $value) { if (in_array($value, $dup_vals)) { if (!isset($dups[$value])) { $dups[$value]=array($key); }else{ array_push($dups[$value],$key); } } } return $dups; } 

Мне очень нравится, что Франсуа отвечает, вот что я придумал, чтобы сохранить ключи. Сначала я отвечу на первый вопрос:

 $array = array('2011-06-21', '2011-06-22', '2011-06-22'); /** * flip an array like array_flip but * preserving multiple keys per an array value * * @param array $a * @return array */ function array_flip_multiple(array $a) { $result = array(); foreach($a as $k=>$v) $result[$v][]=$k ; return $result; } $hash = array_flip_multiple($array); // filter $hash based on your specs (2 or more) $hash = array_filter($hash, function($items) {return count($items) > 1;}); // get all remaining keys $keys = array_reduce($hash, 'array_merge', array()); var_dump($array, $hash, $keys); 

выход:

 # original array array(3) { [0]=> string(10) "2011-06-21" [1]=> string(10) "2011-06-22" [2]=> string(10) "2011-06-22" } # hash (filtered) array(1) { ["2011-06-22"]=> array(2) { [0]=> int(1) [1]=> int(2) } } # the keys array(2) { [0]=> int(1) [1]=> int(2) } 

Итак, теперь второй вопрос:

Просто используйте $hash для получения ключей для значения:

var_dump($hash['2011-06-22']); возвращает ключи.

Преимущество в том, что если вам нужно проверить несколько значений, данные уже хранятся в хеше и доступны для использования.

 $array = array( '2011-06-21','2011-06-22','2011-06-22','2011-06-23', '2011-06-23','2011-06-24','2011-06-24','2011-06-25', '2011-06-25','2011-06-26','2011-06-26','2011-06-27', '2011-06-27','2011-06-28','2011-06-29','2011-06-29', '2011-06-30','2011-06-30','2011-07-01','2011-07-01', '2011-07-02','2011-07-02','2011-07-03','2011-07-03', '2011-07-04','2011-07-04','2011-07-05','2011-07-05', '2011-07-06','2011-07-06','2011-07-07','2011-07-07', ); function getDupKeys(array $array, $return_first = true, $return_by_key = true) { $seen = array(); $dups = array(); foreach ($array as $k => $v) { $vk = $return_by_key ? $v : 0; if (!array_key_exists($v, $seen)) { $seen[$v] = $k; continue; } if ($return_first && !array_key_exists($v, $dups)) { $dups[$vk][] = $seen[$v]; } $dups[$vk][] = $k; } return $return_by_key ? $dups : $dups[0]; } 

Если оба необязательных параметра верны, он возвращает массив массивов; ключ каждого дочернего массива будет значением, которое не было уникальным, а значениями массива будут все те ключи, которые имели это значение.

Если первый необязательный параметр является ложным, тогда будут возвращены только ключи после первого экземпляра не уникального значения (т. Е. Для данного массива каждое значение возвращает только один ключ, во второй раз, когда это произошло, вместо первого) ,

Если второй параметр является необязательным, то вместо возврата массива массивов он возвращает плоский массив, содержащий все повторяющиеся ключи (именно те ключи, которые он возвращает, продиктованы предыдущим необязательным параметром).

Вот дамп print_r, потому что он красивее:

 print_r(getDupKeys($array)); Array ( [2011-06-22] => Array ( [0] => 1 [1] => 2 ) [2011-06-23] => Array ( [0] => 3 [1] => 4 ) [2011-06-24] => Array ( [0] => 5 [1] => 6 ) [2011-06-25] => Array ( [0] => 7 [1] => 8 ) [2011-06-26] => Array ( [0] => 9 [1] => 10 ) [2011-06-27] => Array ( [0] => 11 [1] => 12 ) [2011-06-29] => Array ( [0] => 14 [1] => 15 ) [2011-06-30] => Array ( [0] => 16 [1] => 17 ) [2011-07-01] => Array ( [0] => 18 [1] => 19 ) [2011-07-02] => Array ( [0] => 20 [1] => 21 ) [2011-07-03] => Array ( [0] => 22 [1] => 23 ) [2011-07-04] => Array ( [0] => 24 [1] => 25 ) [2011-07-05] => Array ( [0] => 26 [1] => 27 ) [2011-07-06] => Array ( [0] => 28 [1] => 29 ) [2011-07-07] => Array ( [0] => 30 [1] => 31 ) ) 

 print_r(getDupKeys($array, false)); Array ( [2011-06-22] => Array ( [0] => 2 ) [2011-06-23] => Array ( [0] => 4 ) [2011-06-24] => Array ( [0] => 6 ) [2011-06-25] => Array ( [0] => 8 ) [2011-06-26] => Array ( [0] => 10 ) [2011-06-27] => Array ( [0] => 12 ) [2011-06-29] => Array ( [0] => 15 ) [2011-06-30] => Array ( [0] => 17 ) [2011-07-01] => Array ( [0] => 19 ) [2011-07-02] => Array ( [0] => 21 ) [2011-07-03] => Array ( [0] => 23 ) [2011-07-04] => Array ( [0] => 25 ) [2011-07-05] => Array ( [0] => 27 ) [2011-07-06] => Array ( [0] => 29 ) [2011-07-07] => Array ( [0] => 31 ) ) 

 print_r(getDupKeys($array, true, false)); Array ( [0] => 1 [1] => 2 [2] => 3 [3] => 4 [4] => 5 [5] => 6 [6] => 7 [7] => 8 [8] => 9 [9] => 10 [10] => 11 [11] => 12 [12] => 14 [13] => 15 [14] => 16 [15] => 17 [16] => 18 [17] => 19 [18] => 20 [19] => 21 [20] => 22 [21] => 23 [22] => 24 [23] => 25 [24] => 26 [25] => 27 [26] => 28 [27] => 29 [28] => 30 [29] => 31 ) 

 print_r(getDupKeys($array, false, false)); Array ( [0] => 2 [1] => 4 [2] => 6 [3] => 8 [4] => 10 [5] => 12 [6] => 15 [7] => 17 [8] => 19 [9] => 21 [10] => 23 [11] => 25 [12] => 27 [13] => 29 [14] => 31 )