删除空数组元素

1034

我的数组中有一些来自用户的空字符串元素。在执行以下操作后,$linksArray 仍然具有空元素:

foreach($linksArray as $link)
{
    if($link == '')
    {
        unset($link);
    }
}
print_r($linksArray);

empty() 函数也不起作用。


4
值得一提的是,上面的代码无法运行,因为unset(...)操作的是由foreach循环创建的变量,而不是明显保持不变的原始数组。 - savedario
1
如果(!empty($link)) { echo $link; } 这对我有效 - Shiplu
2
您正在更改一个未被引用的 $link!请使用 foreach($linksArray as $key => $link) unset(linksArray[$key])。 - Nijboer IT
https://dev59.com/lm855IYBdhLWcg3wSiU7#66004034 - Billu
27个回答

1993
当你处理字符串数组时,你可以简单地使用array_filter()函数,它会方便地为你处理所有这些:
$linksArray = array_filter($linksArray);

请记住,如果没有提供回调函数,所有等于FALSE的数组元素(参见转换为布尔值)都将被删除。因此,如果您需要保留例如精确字符串'0'的元素,您将需要一个自定义的回调函数:
// PHP 7.4 and later
print_r(array_filter($linksArray, fn($value) => !is_null($value) && $value !== ''));

// PHP 5.3 and later
print_r(array_filter($linksArray, function($value) { return !is_null($value) && $value !== ''; }));

// PHP < 5.3
print_r(array_filter($linksArray, create_function('$value', 'return $value !== "";')));

注意:如果您需要在删除空元素后重新索引数组,请使用以下方法:
$linksArray = array_values(array_filter($linksArray));

17
array_filter 应该移除空元素。如果PHP的“空”定义与您的定义不完全相同,则可以使用匿名函数作为回调选项来删除不需要的元素。显然,您必须具备 PHP 5.3 或更高版本才能使用匿名回调函数。https://dev59.com/iHE95IYBdhLWcg3wMrEB - Buttle Butkus
87
注意array_filter不会重新索引数组索引(在使用for语句中处理数组时可能会出现问题)。所以请用array_values函数将其全部包装起来。 - Michal - wereda-net
11
答案不正确,因为它也会删除“false”元素。(http://php.net/manual/zh/function.array-filter.php) - pliashkou
5
你尝试过在筛选数组之前打印它吗?我认为第二次设置a只是重置了第一个。 - Cullub
7
@Cranio提到的内容已经被另一个评论涵盖了。这并不是错误,但可能比您的要求更加宽泛。这并不意味着其他人不能仍然觉得它有用; 毕竟,如果您的数组中只有字符串,那么此答案将仅删除空字符串。 - Martijn Pieters
显示剩余14条评论

200
你可以使用array_filter来移除空元素:
$emptyRemoved = array_filter($linksArray);
如果你的数组中有(int) 0,你可以使用以下方法:
$emptyRemoved = remove_empty($linksArray);

function remove_empty($array) {
  return array_filter($array, '_remove_empty_internal');
}

function _remove_empty_internal($value) {
  return !empty($value) || $value === 0;
}

编辑:也许你的元素本身不是空的,而是包含一个或多个空格... 在使用array_filter之前,您可以使用以下方法:

$trimmedArray = array_map('trim', $linksArray);

11
我刚刚在BoltClock的回答中添加了这句话,你可以简单地使用array_filter($foo, 'strlen')来避免“0”的问题,并且只删除长度为零的内容。 - A.B. Carroll
2
@nezZario: 假设你的数组里只有scalar元素,是的。否则,你无法这样做。 - Andrew Moore
2
使用lambda表达式来处理PHP >= 5.3的代码:function remove_empty($array) { return array_filter($array, function($value){return !empty($value) || $value === 0;}); } - viral
2
array_map() 做了魔法,因为我在那些空数组中有空格! - Prodigy

187
这个话题上最受欢迎的答案完全是错误的。
考虑以下 PHP 脚本:
<?php
$arr = array('1', '', '2', '3', '0');
// Incorrect:
print_r(array_filter($arr));
// Correct:
print_r(array_filter($arr, 'strlen'));

这是为什么呢?因为包含单个'0'字符的字符串也会被计算为布尔假,所以即使它不是空字符串,它也会被过滤掉。那将是一个错误。

将内置的strlen函数作为过滤函数传递将起作用,因为对于非空字符串它返回一个非零整数,而对于空字符串它返回零整数。非零整数在转换为布尔值时始终计算为true,而零整数在转换为布尔值时始终计算为false。

因此,绝对、明确、正确的答案是:

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

6
同意。对于那些数组包含字符串的人来说,这应该是被接受的答案。 - mwieczorek
2
点赞。这个回答比其他许多回答更好,但需要注意的是,目前被接受的答案在技术上并不是不正确的,因为“empty”确实在PHP中具有特殊含义。(一些符合“empty”的值:0""null - rinogo
7
他们并没有错误,一切都取决于上下文。在某些情况下,保留数值0可能非常重要。所以,请不要说除了你之外所有人都错了。 - Macr1408
12
如果数组中包含另一个数组,这将出现错误:strlen() 期望参数1是字符串,但提供的是数组 - hpaknia
1
你可以说这也是一个不错的方法(而不是指出别人的错误)来实现自己想要的行动。基本上并非所有情况都相似。虽然这种方法对我的情况有效。 - MR_AMDEV
显示剩余3条评论

110

4
我在谷歌搜索了这个问题后也尝试过。不幸的是,它为我留下了空白元素。 - Will
2
@Will:你确定吗?它也会删除空字符串,我已经成功测试过了。也许你的输入值包含空格,应该在处理之前进行修剪。根据布尔转换规则,空字符串被评估为false,因此被array_filter删除。 - acme

58
    $myarray = array_filter($myarray, 'strlen');  //removes null values but leaves "0"
    $myarray = array_filter($myarray);            //removes all null values

strlen也会移除false :( - pyronaur
1
只有当false是一个字符串时,它才有长度。布尔值false没有字符串长度。 - mickmackusa
从PHP8.1开始,strlen不再是一种好的技术,因为它会生成过时警告。Deprecated: strlen(): Passing null to parameter #1 ($string) of type string is deprecated - mickmackusa

45
你只需要这样做。
array_filter($array)

array_filter: “如果没有提供回调函数,则会删除输入的所有等于FALSE的条目。”这意味着具有值NULL、0、'0'、''、FALSE、array() 的元素也将被删除。

另一个选项是执行

array_diff($array, array(''))

这将会移除值为 NULL、'' 和 FALSE 的元素。

希望这可以帮到你 :)

更新

这里有一个例子。

$a = array(0, '0', NULL, FALSE, '', array());

var_dump(array_filter($a));
// array()

var_dump(array_diff($a, array(0))) // 0 / '0'
// array(NULL, FALSE, '', array());

var_dump(array_diff($a, array(NULL))) // NULL / FALSE / ''
// array(0, '0', array())

总结:

  • 0或'0'将移除0和'0'
  • NULL、FALSE或''将移除NULL、FALSE和''

44
foreach($linksArray as $key => $link) 
{ 
    if($link === '') 
    { 
        unset($linksArray[$key]); 
    } 
} 
print_r($linksArray); 

4
一种简洁、可读且安全的解决方案,不会删除 false0。考虑到这篇文章是在被接受的答案发表的同一分钟发布的(那个答案不安全且不正确),我只能假设你获得的8个赞相对于那个被接受的答案的649个赞较少,是因为后者是一个单行的解决方案。 - rybo111
@rybo111 - 可能,但在回调函数中使用array_filter()的逻辑比使用foreach()循环更加清晰。 - Mark Baker
也许更快,但是您的解决方案是最可读的,这很重要。对于那些需要使用trim()的人,我建议使用if(is_string($link)&& trim($link)==='') - rybo111

37

简而言之:

这是我建议的代码:

$myarray =  array_values(array_filter(array_map('trim', $myarray), 'strlen'));

解释:

我认为使用array_filter是不错的选择,但这还不足够,因为像space\n这样的值会保留在数组中,这通常是不好的。

因此,我建议您同时使用array_filterarray_map

array_map用于去除空格,array_filter用于去除空值,strlen用于保留值为0的项,并且如果需要,array_values可用于重新索引。

示例:

$myarray = array("\r", "\n", "\r\n", "", " ", "0", "a");

// "\r", "\n", "\r\n", " ", "a"
$new1 = array_filter($myarray);

// "a"
$new2 = array_filter(array_map('trim', $myarray));

// "0", "a"
$new3 = array_filter(array_map('trim', $myarray), 'strlen');

// "0", "a" (reindex)
$new4 = array_values(array_filter(array_map('trim', $myarray), 'strlen'));

var_dump($new1, $new2, $new3, $new4);

结果:

array(5) {
  [0]=>
" string(1) "
  [1]=>
  string(1) "
"
  [2]=>
  string(2) "
"
  [4]=>
  string(1) " "
  [6]=>
  string(1) "a"
}
array(1) {
  [6]=>
  string(1) "a"
}
array(2) {
  [5]=>
  string(1) "0"
  [6]=>
  string(1) "a"
}
array(2) {
  [0]=>
  string(1) "0"
  [1]=>
  string(1) "a"
}

在线测试:

http://sandbox.onlinephpfunctions.com/code/e02f5d8795938be9f0fa6f4c17245a9bf8777404


35

另一种从您的数组中删除空元素(""空字符串)的一行代码。

$array = array_filter($array, function($a) {return $a !== "";});

注意:此代码有意保留了null0false元素。


或者您可能想先修剪您的数组元素:

$array = array_filter($array, function($a) {
    return trim($a) !== "";
});

注意:此代码还会删除nullfalse元素。


3
正是我所需要的,而且它也兼容旧版PHP,谢谢!;-) - Stano
1
@JohnK 错了。要想完全按照用户的要求进行回调,必须使用回调函数,除非你想移除零和其他假值。 - Cranio

14
如果你正在使用数值数组并需要在删除空元素后重新索引数组,请使用 array_values 函数:
array_values(array_filter($array));

另请参见:PHP重新索引数组?


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接