Как удалить пустые значения из многомерного массива в PHP?

Я искал много ответов, но никто из них не работает для меня.

Это данные, присваиваемые массиву $quantities quantity:

 Array( [10] => Array([25.00] => 1) [9] => Array([30.00] => 3) [8] => Array([30.00] => 4) [12] => Array([35.00] => ) [1] => Array([30.00] => ) [2] => Array([30.00] => ) ) 

Я ищу способ удалить подмассивы с пустыми значениями, такими как [12] [1] и [2] , сохраняя все остальное.

Желаемый результат:

 Array( [10] => Array([25.00] => 1) [9] => Array([30.00] => 3) [8] => Array([30.00] => 4) ) 

Я пробовал много функций на официальных php-документах, и никто из них не работал.

Я использовал этот:

 function array_filter_recursive($array, $callback = null) { foreach ($array as $key => & $value) { if (is_array($value)) { $value = array_filter_recursive($value, $callback); } else { if ( ! is_null($callback)) { if ( ! $callback($value)) { unset($array[$key]); } } else { if ( ! (bool) $value) { unset($array[$key]); } } } } unset($value); return $array; } с function array_filter_recursive($array, $callback = null) { foreach ($array as $key => & $value) { if (is_array($value)) { $value = array_filter_recursive($value, $callback); } else { if ( ! is_null($callback)) { if ( ! $callback($value)) { unset($array[$key]); } } else { if ( ! (bool) $value) { unset($array[$key]); } } } } unset($value); return $array; } с function array_filter_recursive($array, $callback = null) { foreach ($array as $key => & $value) { if (is_array($value)) { $value = array_filter_recursive($value, $callback); } else { if ( ! is_null($callback)) { if ( ! $callback($value)) { unset($array[$key]); } } else { if ( ! (bool) $value) { unset($array[$key]); } } } } unset($value); return $array; } с function array_filter_recursive($array, $callback = null) { foreach ($array as $key => & $value) { if (is_array($value)) { $value = array_filter_recursive($value, $callback); } else { if ( ! is_null($callback)) { if ( ! $callback($value)) { unset($array[$key]); } } else { if ( ! (bool) $value) { unset($array[$key]); } } } } unset($value); return $array; } 

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

Я не хочу этого:

 Array( [10] => Array([25.00] => 1) [9] => Array([30.00] => 3) [8] => Array([30.00] => 4) [12] => Array() [1] => Array() [2] => Array() ) 

Немного поздно, но может помочь кому-то найти тот же ответ. Я использовал этот очень простой подход;

  1. удалите все ключи из вложенных массивов, которые не содержат значения, затем
  2. удалите все пустые вложенные массивы.

 $postArr = array_map('array_filter', $postArr); $postArr = array_filter( $postArr ); 

Для моего дела работала следующая функция. Мы можем использовать простую рекурсивную функцию для удаления всех пустых элементов из многомерного массива PHP:

 function array_filter_recursive($input){ foreach ($input as &$value){ if (is_array($value)){ $value = array_filter_recursive($value); } } return array_filter($input); } 

Тогда нам просто нужно вызвать эту функцию:

 $myArray = array_filter_recursive($myArray); 

Не уверен, что это именно то, что вы ищете.

 function array_remove_null($array) { foreach ($array as $key => $value) { if(is_null($value)) unset($array[$key]); if(is_array($value)) $array[$key] = array_remove_null($value); } return $array; } с function array_remove_null($array) { foreach ($array as $key => $value) { if(is_null($value)) unset($array[$key]); if(is_array($value)) $array[$key] = array_remove_null($value); } return $array; } 

Обновление (исправления):

 function array_remove_null($array) { foreach ($array as $key => $value) { if(is_null($value)) unset($array[$key]); if(is_string($value) && empty($value)) unset($array[$key]); if(is_array($value)) $array[$key] = array_remove_null($value); if(isset($array[$key]) && count($array[$key])==0) unset($array[$key]); } return $array; } с function array_remove_null($array) { foreach ($array as $key => $value) { if(is_null($value)) unset($array[$key]); if(is_string($value) && empty($value)) unset($array[$key]); if(is_array($value)) $array[$key] = array_remove_null($value); if(isset($array[$key]) && count($array[$key])==0) unset($array[$key]); } return $array; } с function array_remove_null($array) { foreach ($array as $key => $value) { if(is_null($value)) unset($array[$key]); if(is_string($value) && empty($value)) unset($array[$key]); if(is_array($value)) $array[$key] = array_remove_null($value); if(isset($array[$key]) && count($array[$key])==0) unset($array[$key]); } return $array; } с function array_remove_null($array) { foreach ($array as $key => $value) { if(is_null($value)) unset($array[$key]); if(is_string($value) && empty($value)) unset($array[$key]); if(is_array($value)) $array[$key] = array_remove_null($value); if(isset($array[$key]) && count($array[$key])==0) unset($array[$key]); } return $array; } 

Я уверен, что лучше проверить и сделать это более надежным может помочь решение.

используйте array_map () для фильтрации каждого массива в $ array:

 $newArray = array_map('array_filter', $array); 

Вот демонстрация

 $newArray = array_map('array_filter', $array); 

Этот синтакс – это работа и очень помогает парням полного счастья.

Используйте array_filter с array_map как array_map ниже:

 $arr=array_filter(array_map('array_filter', $arr)); 

Это удаляет все элементы с нулевыми значениями рекурсивно на многопользовательских массивах. Работает на PHP> = 5.6. Если вы хотите удалить все значения «empry», замените !is_null($value) !empty($value) .

 function recursivelyRemoveItemsWithNullValuesFromArray(array $data = []): array { $data = array_map(function($value) { return is_array($value) ? recursivelyRemoveItemsWithNullValuesFromArray($value) : $value; }, $data); return array_filter($data, function($value) { return !is_null($value); }); } 

Поскольку подмассивы в вашем массиве имеют только один элемент, вы можете упростить подход, используя любой из двух следующих методов. Логическое преимущество заключается в том, чтобы избежать функционального итератора ( array_filter ) на элементах второго уровня. Вот почему current() более подходит для этого вопроса / страницы.

Код: ( Демо )

 $quantities=[ 10=>['25.00'=>1], 9=>['30.00'=>3], 8=>['30.00'=>4], 12=>['35.00'=>null], 1=>['30.00'=>''], 2=>['30.00'=>null] ]; var_export(array_filter($quantities,function($a){return strlen(current($a));})); 

ИЛИ

 foreach($quantities as $key=>$sub){ // could be done "by reference" but that impacts code stability if(!strlen(current($sub))){ // if subarray value has no length unset($quantities[$key]); } } var_export($quantities); не foreach($quantities as $key=>$sub){ // could be done "by reference" but that impacts code stability if(!strlen(current($sub))){ // if subarray value has no length unset($quantities[$key]); } } var_export($quantities); 

Оба выводят тот же результат (который намеренно удаляет пустые значения и сохраняет 0 значений)

 array ( 10 => array ( '25.00' => 1, ), 9 => array ( '30.00' => 3, ), 8 => array ( '30.00' => 4, ), ) 

В приведенных выше методах strlen() используется для проверки элементов 2-го уровня, поскольку только ОП перечисляет целые числа как «непустые» значения. У будущих читателей SO могут быть разные требования, основанные на элементах, которые могут содержать false , null , '0' , 0 и т. Д. Подходящими функциями замены для strlen() могут быть: любая из функций is_ , empty () , любая из функции «ctype» и многое другое.

Если массив 2-го уровня OP содержал более одного элемента, и OP хотел удалить все нулевые, ложные-y, пустые, нулевые элементы (что означает, что нули не нужны или не гарантируются), тогда ответ Alastair F будет лучший выбор.

Если входной массив OP имел неизвестное количество уровней И нуль-ish / false-y / empty / null элементы должны быть удалены, то ответ Резы Мамун является логическим, рекурсивным подходом.

Моя точка зрения (и моя мотивация тратить столько времени и на то, чтобы ответить на этот вопрос), что array_filter() жадный, и если вы не знаете об этом поведении по умолчанию, ваш проект может молча выводить неверную информацию. Надеюсь, это объяснение избавит программистов от времени и раздоров.