- Каков наиболее эффективный способ проверить, является ли массив плоским массивом примитивных значений или это многомерный массив ?
- Есть ли способ сделать это, не перебирая массив и не выполняя
is_array()
каждый из его элементов?
140
Ответы:
Короткий ответ - нет, вы не можете этого сделать, по крайней мере, неявно зациклившись, если «второе измерение» может быть где угодно. Если он должен быть в первом элементе, вы просто сделаете
is_array($arr[0]);
Но наиболее эффективный общий способ, который я мог найти, - это использовать цикл foreach в массиве, сокращая замыкание всякий раз, когда обнаруживается попадание (по крайней мере, неявный цикл лучше, чем прямой for ()):
$ more multi.php <?php $a = array(1 => 'a',2 => 'b',3 => array(1,2,3)); $b = array(1 => 'a',2 => 'b'); $c = array(1 => 'a',2 => 'b','foo' => array(1,array(2))); function is_multi($a) { $rv = array_filter($a,'is_array'); if(count($rv)>0) return true; return false; } function is_multi2($a) { foreach ($a as $v) { if (is_array($v)) return true; } return false; } function is_multi3($a) { $c = count($a); for ($i=0;$i<$c;$i++) { if (is_array($a[$i])) return true; } return false; } $iters = 500000; $time = microtime(true); for ($i = 0; $i < $iters; $i++) { is_multi($a); is_multi($b); is_multi($c); } $end = microtime(true); echo "is_multi took ".($end-$time)." seconds in $iters times\n"; $time = microtime(true); for ($i = 0; $i < $iters; $i++) { is_multi2($a); is_multi2($b); is_multi2($c); } $end = microtime(true); echo "is_multi2 took ".($end-$time)." seconds in $iters times\n"; $time = microtime(true); for ($i = 0; $i < $iters; $i++) { is_multi3($a); is_multi3($b); is_multi3($c); } $end = microtime(true); echo "is_multi3 took ".($end-$time)." seconds in $iters times\n"; ?> $ php multi.php is_multi took 7.53565130424 seconds in 500000 times is_multi2 took 4.56964588165 seconds in 500000 times is_multi3 took 9.01706600189 seconds in 500000 times
Неявный цикл, но мы не можем замкнуть его, как только будет найдено совпадение ...
$ more multi.php <?php $a = array(1 => 'a',2 => 'b',3 => array(1,2,3)); $b = array(1 => 'a',2 => 'b'); function is_multi($a) { $rv = array_filter($a,'is_array'); if(count($rv)>0) return true; return false; } var_dump(is_multi($a)); var_dump(is_multi($b)); ?> $ php multi.php bool(true) bool(false)
источник
is_multi()
оптимизируйте код, выполнивreturn count($rv)>0
Дважды используйте count (); один раз в режиме по умолчанию и один раз в рекурсивном режиме. Если значения совпадают, массив не является многомерным, так как многомерный массив будет иметь более высокое рекурсивное количество.
if (count($array) == count($array, COUNT_RECURSIVE)) { echo 'array is not multidimensional'; } else { echo 'array is multidimensional'; }
Второе значение этой опции
mode
было добавлено в PHP 4.2.0. Из документации PHP :Однако этот метод не обнаруживает
array(array())
.источник
Для PHP 4.2.0 или новее:
function is_multi($array) { return (count($array) != count($array, 1)); }
источник
array(array())
илиarray(array(), array())
как. Как правило, если внутренний массив пуст, рекурсивный счетчик правильно добавит для него 0, что приведет к совпадению с обычным счетчиком.Я думаю, что это наиболее простой и современный способ:
function is_multidimensional(array $array) { return count($array) !== count($array, COUNT_RECURSIVE); }
источник
Вы можете просто выполнить это:
if (count($myarray) !== count($myarray, COUNT_RECURSIVE)) return true; else return false;
Если необязательный параметр режима установлен в
COUNT_RECURSIVE
(или 1), count () будет рекурсивно подсчитывать массив. Это особенно полезно для подсчета всех элементов многомерного массива.Если он такой же, значит, подуровней нигде нет. Легко и быстро!
источник
if(count($tasks_by_date) !== count($tasks_by_date, 1))
!==
раньше я видел, существует ли подуровень. Для теорий, которые могут искать что-то подобное ... и т. Д.!==
Вы можете проверить
is_array()
первый элемент при условии, что если первый элемент массива является массивом, то и остальные тоже.источник
if( is_array(current($arr)) ) { // is multidimensional }
Все отличные ответы ... вот мои три строчки, которые я всегда использую
function isMultiArray($a){ foreach($a as $v) if(is_array($v)) return TRUE; return FALSE; }
источник
Эта функция вернет целое число измерений массива (украденных отсюда ).
function countdim($array) { if (is_array(reset($array))) $return = countdim(reset($array)) + 1; else $return = 1; return $return; }
источник
Я думаю, вы обнаружите, что эта функция - самый простой, эффективный и быстрый способ.
function isMultiArray($a){ foreach($a as $v) if(is_array($v)) return TRUE; return FALSE; }
Проверить это можно так:
$a = array(1 => 'a',2 => 'b',3 => array(1,2,3)); $b = array(1 => 'a',2 => 'b'); echo isMultiArray($a) ? 'is multi':'is not multi'; echo '<br />'; echo isMultiArray($b) ? 'is multi':'is not multi';
источник
foreach($a as $v) is_array($v) ? return TRUE : return FALSE;
foreach($a as $v) return is_array($v) ? true : false;
После PHP 7 вы могли просто сделать:
public function is_multi(array $array):bool { return is_array($array[array_key_first($array)]); }
источник
Вы также можете выполнить простую проверку, например:
$array = array('yo'=>'dream', 'mydear'=> array('anotherYo'=>'dream')); $array1 = array('yo'=>'dream', 'mydear'=> 'not_array'); function is_multi_dimensional($array){ $flag = 0; while(list($k,$value)=each($array)){ if(is_array($value)) $flag = 1; } return $flag; } echo is_multi_dimensional($array); // returns 1 echo is_multi_dimensional($array1); // returns 0
источник
Попробуйте следующее
if (count($arrayList) != count($arrayList, COUNT_RECURSIVE)) { echo 'arrayList is multidimensional'; }else{ echo 'arrayList is no multidimensional'; }
источник
Даже это работает
Если false - это одномерный массив, если true - многомерный массив.
current предоставит вам первый элемент вашего массива и проверит, является ли первый элемент массивом или нет, с помощью функции is_array .
источник
Не используйте COUNT_RECURSIVE
нажмите на этот сайт, чтобы узнать почему
используйте rsort, а затем используйте isset
function is_multi_array( $arr ) { rsort( $arr ); return isset( $arr[0] ) && is_array( $arr[0] ); } //Usage var_dump( is_multi_array( $some_array ) );
источник
В моем случае. Я попал в очень странное состояние.
1-й случай =
array("data"=> "name");
2-й случай =
array("data"=> array("name"=>"username","fname"=>"fname"));
Но если
data
вместо значения есть массив, тогда функция sizeof () или count () не работает для этого условия. Затем я создаю настраиваемую функцию для проверки.Если первый индекс массива имеет значение, он возвращает «только значение».
Но если индекс имеет массив вместо значения, он возвращает «имеет массив».
Я использую этот способ
function is_multi($a) { foreach ($a as $v) { if (is_array($v)) { return "has array"; break; } break; } return 'only value'; }
Особая благодарность Винко Врсаловичу
источник
Я думаю, что это классно (реквизит для другого пользователя, я не знаю его имени пользователя):
static public function isMulti($array) { $result = array_unique(array_map("gettype",$array)); return count($result) == 1 && array_shift($result) == "array"; }
источник
Все вышеперечисленные методы слишком сложны для быстрого развертывания. Если массив плоский, тестирование первого элемента должно вернуть примитив, например int, string и т. Д. Если массив многомерный, он должен вернуть массив. Кроме того, вы можете использовать этот один лайнер быстро и аккуратно.
echo is_array(array_shift($myArray));
если это вернет истину, массив является многомерным. Остальное плоское. Следует отметить, что массивы очень редко имеют разные размеры, например, если вы генерируете данные из модели, она всегда будет иметь один и тот же тип многомерной или плоской структуры, по которой можно обходить циклы. Если это не так, то вы создали его вручную, что означает, что вы знаете, где все будет находиться, и он просто работает без необходимости писать алгоритм цикла.
источник
array_shift()
, так как он удаляет первый элемент, а также сбрасывает цифровые клавиши! Лучше использовать,current()
если все еще хочется однострочника.В дополнение к предыдущим ответам и в зависимости от схемы массива, который вы хотите проверить:
function is_multi_array($array=[],$mode='every_key'){ $result = false; if(is_array($array)){ if($mode=='first_key_only'){ if(is_array(array_shift($array))){ $result = true; } } elseif($mode=='every_key'){ $result = true; foreach($array as $key => $value){ if(!is_array($value)){ $result = false; break; } } } elseif($mode=='at_least_one_key'){ if(count($array)!==count($array, COUNT_RECURSIVE)){ $result = true; } } } return $result; }
источник
Это так просто, как
$isMulti = !empty(array_filter($array, function($e) { return is_array($e); }));
источник
$is_multi_array = array_reduce(array_keys($arr), function ($carry, $key) use ($arr) { return $carry && is_array($arr[$key]); }, true);
Вот хороший лайнер. Он перебирает каждый ключ, чтобы проверить, является ли значение этого ключа массивом. Это обеспечит истинное
источник
if($array[0]){ //enter your code }
источник
if (isset($array[0])) { }
. Если вы уверены, что индексы массива начинаются с 0if ( array_key_exists(0,$array) ) { // multidimensional array } else { // not a multidimensional array }
* только для массивов с числовым индексом
источник
Собственная функция print_r возвращает удобочитаемую строку. Просто посчитайте экземпляры «Массив».
пытаться...
substr_count(print_r([...array...], true), 'Array') > 1; $a = array(1 => 'a',2 => 'b',3 => array(1,2,3)); $b = array(1 => 'a',2 => 'b'); $c = array(1 => 'a',2 => 'b','foo' => array(1,array(2))); $d = array(array()); $e = array(1, array()); $f = array(array(), array()); $g = array("hello", "hi" => "hi there"); $h[] = $g; var_dump(substr_count(print_r($a, true), 'Array') > 1); ... //a: bool(true) //b: bool(false) //c: bool(true) //d: bool(true) //e: bool(true) //f: bool(true) //g: bool(false) //h: bool(true)
На моем ящике "is_multi занял 0,83681297302246 секунд в 500000 раз"
Предоставлено: Руах ха-Кодеш
источник
function isMultiArray(array $value) { return is_array(reset($value)); }
источник
Никаких петель, просто и понятно.
Работает также с ассоциированными массивами, а не только с числовыми массивами, которые не могут содержать 0 (как в предыдущем примере, вы получите предупреждение, если массив не имеет 0).
источник