如何在PHP中检查JSON对象是否为空?

27

我正在使用PHP读取JSON数据,其中的数据包含了空对象(例如{})。因此问题是,我必须以不同的方式处理对象为空的情况,但我找不到足够好的方法来进行检查。 empty(get_object_vars(object)) 看起来太可怕且效率低下。有没有更好的方法来进行检查?


相关:https://dev59.com/z2ox5IYBdhLWcg3wIQ5o - YakovL
5个回答

35

您要反序列化多少个对象?除非empty(get_object_vars($object))或将其强制转换为数组证明是主要的减速/瓶颈,否则我不会担心 - Greg的解决方案很好。

我建议在解码JSON数据时使用$associative标志:

json_decode($data, true)

使用这个方法可以将JSON对象解码为普通的PHP数组,而不是stdClass对象。然后就可以使用empty()检查空对象,并创建一个用户定义类的对象,而不是使用stdClass,这可能是从长远来看一个不错的选择。


1
但是,如果你找到了一个普通的 PHP 数组,你怎么知道它是从 [] 还是 {} 编码而来的呢?在 PHP 中它们并没有区别,但在 JSON 中是有区别的。 - David Spector

28

你可以将它转换为数组(不幸的是,你不能在调用 empty() 的时候这样做):

$x = (array)$obj;
if (empty($x))
    ...

或将其转换为数组并使用 count()

if (count((array)$obj))
    ...

与 get_object_vars 不是一样的吗?也就是说,不是很高效? :) - vava
2
我还没有测试过,但除非你遇到性能问题并已将其识别为瓶颈,否则我认为不值得让自己担心。 - Greg
1
如果你大部分时间都是C++程序员,那么停止担心不必要的数组转换并不容易 :) 这意味着为了执行仅需快速检查位设置的操作而进行内存分配和复制。 - vava
在JSON中,数组的计数对于区分[]和{}是无用的。 - David Spector

4

尝试不使用empty()函数,该函数为:

get_object_vars($obj) ? TRUE : FALSE;

PHP文档中,我们可以读到如下说明:

当使用empty()函数检查不可访问的对象属性时,如果已声明,则会调用__isset()重载方法。

这意味着当在具有__get()方法的对象上使用empty()函数时,它将始终返回True。

0

我需要判断一个对象是否为空,但是我也需要忽略私有和受保护的属性,所以我写了这个小函数来实现。

function empty_obj(&$object, $ignore_private = true, $ignore_protected = true) {
  $obj_name = get_class($object);
  $obj = (array)$object;

  foreach(array_keys($obj) as $prop) {
    $is_private = $is_protected = false;

    $prop = preg_replace("/[^\w*]/", '', $prop);
    $prop_name = str_replace(array($obj_name, '*'), '', $prop);

    if(preg_match("~^$obj_name$prop_name$~", $prop))
      $is_private = true;
    if(preg_match("~^\*$prop_name$~", $prop))
      $is_protected = true;

    if(!$is_private || !$is_protected || ($is_private && !$ignore_private) || ($is_protected && !$ignore_protected))
      return;
  }
  return true;
}

0

我不确定这是否比转换为数组更有效,但我猜会更有效。你可以开始循环对象,一旦找到答案就停止循环。

function is_obj_empty($obj){
   if( is_null($obj) ){
      return true;
   }
   foreach( $obj as $key => $val ){
      return false;
   }
   return true;
}

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