Php count()发出E_警告
在PHP7.2之前,对标量值或不可数对象使用将返回Php count()发出E_警告,php,php-7.2,Php,Php 7.2,在PHP7.2之前,对标量值或不可数对象使用将返回1或0 例如: 在中,如上所示使用count()将发出警告消息 尝试计数()不可计数类型(包括sizeof()别名函数)时,将发出E_警告 警告:count():参数必须是实现可计数的数组或对象 因此,许多流行的框架将提升E_警告,并抛出异常 [ErrorException]count():参数必须是实现可计数的数组或对象 PHP开发人员还对错误提升行为进行了评论 显示警告或将其转换为更严重错误/异常的环境将受到影响,但这应该引起对代码中错误的
1
或0
例如:
在中,如上所示使用count()
将发出警告消息
尝试计数()不可计数类型(包括sizeof()别名函数)时,将发出E_警告
警告:count():参数必须是实现可计数的数组或对象
因此,许多流行的框架将提升E_警告
,并抛出异常
[ErrorException]count():参数必须是实现可计数的数组或对象
PHP开发人员还对错误提升行为进行了评论
显示警告或将其转换为更严重错误/异常的环境将受到影响,但这应该引起对代码中错误的注意
在PHP7.2+中,如果不修改错误报告设置,也不使用
@count()
,那么如何在不发出E_警告的情况下实现count()
?问题是,对未实现可数接口的标量或对象调用count()
,返回1,可以很容易地隐藏bug
鉴于以下情况:
function handle_records(iterable $iterable)
{
if (count($iterable) === 0) {
return handle_empty();
}
foreach ($iterable as $value) {
handle_value($value);
}
}
传递一个不产生任何结果的生成器不会调用handle\u empty()
或handle\u value()
此外,没有迹象表明两人都没有被调用
默认情况下,这仍将返回1
,但会另外记录警告。如果有的话,这个警告会引起对代码中潜在错误的注意
有关更多信息,请参阅。正如我们所讨论的,有多种方法可以实现count()
的原始功能,并且不会发出E\u警告
在PHP7.3中添加了一个新函数,专门用于解决E_警告
问题,以及应用程序在其代码中普遍采用is_数组($var)|$var instanceof\Countable
在PHP7.2中,尝试计数不可数时添加了警告
东西。在那之后,每个人都被迫搜索和更改他们的密码
代码,以避免它。通常情况下,下面的一段代码
标准:
if(是_数组($foo)| |$foo instanceof Countable){
//$foo是可数的
}
自定义函数替换
出于这个原因,解决这个问题的最佳方法似乎是执行与PHP使用的is\u countable
相同的功能,并创建一个自定义函数以确保符合count
的原始功能
示例
结果
array: 3
string: 1
number: 1
iterator: 3
countable: 3
zero: 1
string_zero: 1
object: 1
stdClass: 1
null: 0
empty: 1
boolt: 1
boolf: 1
Notice: Undefined variable: undefined in /in/8M0Wd on line 53
undefined: 0
array: 3
string: 1
number: 1
iterator: 3
countable: 3
zero: 1
string_zero: 1
object: 1
stdClass: 1
null: 0
empty: 1
boolt: 1
boolf: 1
---
Undefined: 0
垫片是可计数的()
函数
使用上述替换函数,还可以在PHP中填充is_countable
,您可以使用“?”运算符解决该问题。如果左侧为空,则使用右侧。因此,当我们有一个空数组时,我们的结果将是零
计数(空???[])
另一种方法是将其类型转换为数组
计数((数组)null)
您传递字符串/数字时,首先要使用的函数是错误的。我要回滚到7.1。PHP开发人员应该把7.2变成8.0;普遍接受的版本号控制准则说,当更改破坏向后兼容性时,增加主(第一个)号。期望一个小补丁(增加到第二个数字)没有这样的中断不是不合理的。你实际上是在问“模仿count()的最佳方法是什么”,这对于SO来说不是一个有效的问题。因为它将获得多个答案,产生固执己见的结果。在您看来,@
是不好的,尽管它产生了预期的结果,但这是由于您非常合理的考虑。长期可维护性也是主观的。归根结底,您希望继续以一种非预期的方式使用count,这一点自2013年以来就有了记录。IMO最好的方法是重构代码,使其与7.2+兼容,原因如下所述;我只是想知道stackoverflow发生了什么事。无论如何,谢谢你给我答案的链接。遗憾的是,它不能发布在这里,我很想得到这些解决方案的反馈,或者给出反馈。真的很遗憾。这就是为什么人们使用stackoverflow来寻找问题的解决方案,而不仅仅是批评一个对许多开发人员来说非常重要的问题。我很感激这个问题和所有的答案。嗯,你没有错。问题是,这就是这个函数的工作原理。如果你不了解这个函数是如何工作的,它可能会导致bug。他们现在所做的是,他们改变了一个核心函数,因为有人不喜欢旧函数。打破了很多库。我只是在像这样计数之前将变量设置为数组。如果(!is_array($arrayVariable)){$arrayVariable=array();}
array: 3
string: 1
number: 1
iterator: 3
countable: 3
zero: 1
string_zero: 1
object: 1
stdClass: 1
null: 0
empty: 1
boolt: 1
boolf: 1
Notice: Undefined variable: undefined in /in/8M0Wd on line 53
undefined: 0
if (!\function_exists('is_countable')) {
function is_countable($value)
{
return \is_array($value) || $value instanceof \Countable;
}
}
function countValid($array_or_countable, $mode = \COUNT_NORMAL)
{
if (\is_countable($array_or_countable)) {
return \count($array_or_countable, $mode);
}
return null === $array_or_countable ? 0 : 1;
}
@count($var);
array: 3
string: 1
number: 1
iterator: 3
countable: 3
zero: 1
string_zero: 1
object: 1
stdClass: 1
null: 0
empty: 1
boolt: 1
boolf: 1
---
Undefined: 0
\rename_function('count', 'old_count');
\override_function('count', '$array_or_countable,$mode', 'return countValid($array_or_countable,$mode);');
if (!\function_exists('is_countable')) {
function is_countable($value)
{
return \is_array($value) || $value instanceof \Countable;
}
}
function countValid($array_or_countable, $mode = \COUNT_NORMAL)
{
if (\is_countable($array_or_countable)) {
return \old_count($array_or_countable, $mode);
}
return null === $array_or_countable ? 0 : 1;
}