简体   繁体   English

不能使用 stdClass 类型的对象作为数组?

[英]Cannot use object of type stdClass as array?

I get a strange error using json_decode() .使用json_decode()出现奇怪的错误。 It decode correctly the data (I saw it using print_r ), but when I try to access to info inside the array I get:它正确解码数据(我使用print_r看到它),但是当我尝试访问数组内的信息时,我得到:

Fatal error: Cannot use object of type stdClass as array in
C:\Users\Dail\software\abs.php on line 108

I only tried to do: $result['context'] where $result has the data returned by json_decode()我只尝试这样做: $result['context']其中$resultjson_decode()返回的数据

How can I read values inside this array?如何读取此数组中的值?

使用json_decode的第二个参数使其返回一个数组:

$result = json_decode($data, true);

The function json_decode() returns an object by default.函数json_decode()默认返回一个对象。

You can access the data like this:您可以像这样访问数据:

var_dump($result->context);

If you have identifiers like from-date (the hyphen would cause a PHP error when using the above method) you have to write:如果您有像from-date这样的标识符(使用上述方法时连字符会导致 PHP 错误),您必须编写:

var_dump($result->{'from-date'});

If you want an array you can do something like this:如果你想要一个数组,你可以这样做:

$result = json_decode($json, true);

Or cast the object to an array:或者将对象强制转换为数组:

$result = (array) json_decode($json);

You must access it using -> since its an object.您必须使用->访问它,因为它是一个对象。

Change your code from:更改您的代码:

$result['context'];

To:到:

$result->context;

Use true as the second parameter to json_decode .使用true作为json_decode的第二个参数。 This will decode the json into an associative array instead of stdObject instances:这会将 json 解码为关联数组而不是stdObject实例:

$my_array = json_decode($my_json, true);

See the documentation for more details.有关更多详细信息,请参阅文档

Have same problem today, solved like this:今天遇到同样的问题,解决方法如下:

If you call json_decode($somestring) you will get an Object and you need to access like $object->key , but if u call json_decode($somestring, true) you will get an dictionary and can access like $array['key']如果你调用json_decode($somestring)你会得到一个 Object 并且你需要像$object->key一样访问,但是如果你调用json_decode($somestring, true)你会得到一个字典并且可以像$array['key']一样访问$array['key']

It's not an array, it's an object of type stdClass.它不是一个数组,它是一个 stdClass 类型的对象。

You can access it like this:您可以像这样访问它:

echo $oResult->context;

More info here: What is stdClass in PHP?这里有更多信息: PHP 中的 stdClass 是什么?

As the Php Manual say,正如PHP 手册所说,

print_r — Prints human-readable information about a variable print_r — 打印关于变量的人类可读信息

When we use json_decode();当我们使用json_decode(); , we get an object of type stdClass as return type. ,我们得到一个 stdClass 类型的对象作为返回类型。 The arguments, which are to be passed inside of print_r() should either be an array or a string.要在print_r()内部传递的参数应该是数组或字符串。 Hence, we cannot pass an object inside of print_r() .因此,我们不能在print_r()内部传递对象。 I found 2 ways to deal with this.我找到了 2 种方法来处理这个问题。

  1. Cast the object to array.将对象强制转换为数组。
    This can be achieved as follows.这可以如下实现。

     $a = (array)$object;
  2. By accessing the key of the Object通过访问对象的键
    As mentioned earlier, when you use json_decode();如前所述,当您使用json_decode(); function, it returns an Object of stdClass.函数,它返回一个 stdClass 对象。 you can access the elements of the object with the help of -> Operator.您可以在->运算符的帮助下访问对象的元素。

     $value = $object->key;

One, can also use multiple keys to extract the sub elements incase if the object has nested arrays.一,如果对象有嵌套数组,也可以使用多个键来提取子元素。

$value = $object->key1->key2->key3...;

Their are other options to print_r() as well, like var_dump();它们也是print_r()其他选项,例如var_dump(); and var_export();var_export();

PS : Also, If you set the second parameter of the json_decode(); PS :另外,如果你设置了json_decode();的第二个参数json_decode(); to true , it will automatically convert the object to an array();true ,它会自动将对象转换为array();
Here are some references:以下是一些参考:
http://php.net/manual/en/function.print-r.php http://php.net/manual/en/function.print-r.php
http://php.net/manual/en/function.var-dump.php http://php.net/manual/en/function.var-dump.php
http://php.net/manual/en/function.var-export.php http://php.net/manual/en/function.var-export.php

To get an array as result from a json string you should set second param as boolean true.要从 json 字符串获取数组作为结果,您应该将第二个参数设置为布尔值 true。

$result = json_decode($json_string, true);
$context = $result['context'];

Otherwise $result will be an std object.否则 $result 将是一个 std 对象。 but you can access values as object.但是您可以将值作为对象访问。

  $result = json_decode($json_string);
 $context = $result->context;

Sometimes when working with API you simply want to keep an object an object.有时在使用 API 时,您只想将对象保持为对象。 To access the object that has nested objects you could do the following:要访问具有嵌套对象的对象,您可以执行以下操作:

We will assume when you print_r the object you might see this:我们假设当您打印对象时,您可能会看到:

print_r($response);

stdClass object
(
    [status] => success
    [message] => Some message from the data
    [0] => stdClass object
        (
            [first] => Robert
            [last] => Saylor
            [title] => Symfony Developer
        )
    [1] => stdClass object
        (
            [country] => USA
        )
)

To access the first part of the object:要访问对象的第一部分:

print $response->{'status'};

And that would output "success"这将输出“成功”

Now let's key the other parts:现在让我们来看看其他部分:

$first = $response->{0}->{'first'};
print "First name: {$first}<br>";

The expected output would be "Robert" with a line break.预期输出将是带有换行符的“Robert”。

You can also re-assign part of the object to another object.您还可以将对象的一部分重新分配给另一个对象。

$contact = $response->{0};
print "First Name: " . $contact->{'first'} . "<br>";

The expected output would be "Robert" with a line break.预期输出将是带有换行符的“Robert”。

To access the next key "1" the process is the same.访问下一个键“1”的过程是相同的。

print "Country: " . $response->{1}->{'country'} . "<br>";

The expected output would be "USA"预期输出将是“美国”

Hopefully this will help you understand objects and why we want to keep an object an object.希望这将帮助您理解对象以及为什么我们要将对象保留为对象。 You should not need to convert an object to an array to access its properties.您不需要将对象转换为数组来访问其属性。

Try something like this one!尝试这样的事情!

Instead of getting the context like: (this works for getting array index's)而不是获取像这样的上下文:(这适用于获取数组索引)

$result['context']

try (this work for getting objects)尝试(这项工作用于获取对象)

$result->context

Other Example is: (if $result has multiple data values)其他示例是:(如果$result有多个数据值)

Array
(
    [0] => stdClass Object
        (
            [id] => 15
            [name] => 1 Pc Meal
            [context] => 5
            [restaurant_id] => 2
            [items] => 
            [details] => 1 Thigh (or 2 Drums) along with Taters
            [nutrition_fact] => {"":""}
            [servings] => menu
            [availability] => 1
            [has_discount] => {"menu":0}
            [price] => {"menu":"8.03"}
            [discounted_price] => {"menu":""}
            [thumbnail] => YPenWSkFZm2BrJT4637o.jpg
            [slug] => 1-pc-meal
            [created_at] => 1612290600
            [updated_at] => 1612463400
        )

)

Then try this:然后试试这个:

foreach($result as $results)
{
      $results->context;
}

You can convert stdClass object to array like:您可以将 stdClass 对象转换为数组,如:

$array = (array)$stdClass;

stdClsss to array 到数组的 stdClass

当您尝试将其作为$result['context'] ,您将其视为一个数组,它告诉您实际上正在处理一个对象的错误,那么您应该将其作为$result->context

Here is the function signature:这是函数签名:

mixed json_decode ( string $json [, bool $assoc = false [, int $depth = 512 [, int $options = 0 ]]] )

When param is false, which is default, it will return an appropriate php type.当 param 为 false 时,这是默认值,它将返回一个合适的 php 类型。 You fetch the value of that type using object.method paradigm.您使用 object.method 范式获取该类型的值。

When param is true, it will return associative arrays.当 param 为真时,它将返回关联数组。

It will return NULL on error.它会在出错时返回 NULL。

If you want to fetch value through array, set assoc to true.如果要通过数组获取值,请将 assoc 设置为 true。

I got this error out of the blue because my facebook login suddently stopped working (I had also changed hosts) and throwed this error.我突然收到这个错误,因为我的 facebook 登录突然停止工作(我也更换了主机)并抛出了这个错误。 The fix is really easy修复真的很容易

The issue was in this code问题出在这段代码中

  $response = (new FacebookRequest(
    FacebookSession::newAppSession($this->appId, $this->appSecret),
    'GET',
    '/oauth/access_token',
    $params
  ))->execute()->getResponse(true);

  if (isset($response['access_token'])) {       <---- this line gave error
    return new FacebookSession($response['access_token']);
  }

Basically isset() function expect an array but instead it find an object.基本上 isset() 函数期望一个数组,但它找到一个对象。 The simple solution is to convert PHP object to array using (array) quantifier.简单的解决方案是使用(array)量词将 PHP 对象转换为数组。 The following is the fixed code.以下是固定代码。

  $response = (array) (new FacebookRequest(
    FacebookSession::newAppSession($this->appId, $this->appSecret),
    'GET',
    '/oauth/access_token',
    $params
  ))->execute()->getResponse(true);

Note the use off array() quantifier in first line.请注意第一行中使用 off array() 量词。

instead of using the brackets use the object operator for example my array based on database object is created like this in a class called DB:而不是使用括号使用对象运算符,例如我基于数据库对象的数组是在名为 DB 的类中创建的:

class DB {
private static $_instance = null;
private $_pdo,
        $_query, 
        $_error = false,
        $_results,
        $_count = 0;



private function __construct() {
    try{
        $this->_pdo = new PDO('mysql:host=' . Config::get('mysql/host') .';dbname=' . Config::get('mysql/db') , Config::get('mysql/username') ,Config::get('mysql/password') );


    } catch(PDOException $e) {
        $this->_error = true;
        $newsMessage = 'Sorry.  Database is off line';
        $pagetitle = 'Teknikal Tim - Database Error';
        $pagedescription = 'Teknikal Tim Database Error page';
        include_once 'dbdown.html.php';
        exit;
    }
    $headerinc = 'header.html.php';
}

public static function getInstance() {
    if(!isset(self::$_instance)) {
        self::$_instance = new DB();
    }

    return self::$_instance;

}


    public function query($sql, $params = array()) {
    $this->_error = false;
    if($this->_query = $this->_pdo->prepare($sql)) {
    $x = 1;
        if(count($params)) {
        foreach($params as $param){
            $this->_query->bindValue($x, $param);
            $x++;
            }
        }
    }
    if($this->_query->execute()) {

        $this->_results = $this->_query->fetchAll(PDO::FETCH_OBJ);
        $this->_count = $this->_query->rowCount();

    }

    else{
        $this->_error = true;
    }

    return $this;
}

public function action($action, $table, $where = array()) {
    if(count($where) ===3) {
        $operators = array('=', '>', '<', '>=', '<=');

        $field      = $where[0];
        $operator   = $where[1];
        $value      = $where[2];

        if(in_array($operator, $operators)) {
            $sql = "{$action} FROM {$table} WHERE {$field} = ?";

            if(!$this->query($sql, array($value))->error()) {
            return $this;
            }
        }

    }
    return false;
}

    public function get($table, $where) {
    return $this->action('SELECT *', $table, $where);

public function results() {
    return $this->_results;
}

public function first() {
    return $this->_results[0];
}

public function count() {
    return $this->_count;
}

}

to access the information I use this code on the controller script:要访问我在控制器脚本上使用此代码的信息:

<?php
$pagetitle = 'Teknikal Tim - Service Call Reservation';
$pagedescription = 'Teknikal Tim Sevice Call Reservation Page';
require_once $_SERVER['DOCUMENT_ROOT'] .'/core/init.php';
$newsMessage = 'temp message';

$servicecallsdb = DB::getInstance()->get('tt_service_calls', array('UserID',
 '=','$_SESSION['UserID']));

if(!$servicecallsdb) {
// $servicecalls[] = array('ID'=>'','ServiceCallDescription'=>'No Service Calls');
} else {
$servicecalls = $servicecallsdb->results();
}
include 'servicecalls.html.php';



?>

then to display the information I check to see if servicecalls has been set and has a count greater than 0 remember it's not an array I am referencing so I access the records with the object operator "->" like this:然后为了显示信息,我检查了 servicecalls 是否已设置并且计数大于 0 记住它不是我正在引用的数组,因此我使用对象运算符“->”访问记录,如下所示:

<?php include $_SERVER['DOCUMENT_ROOT'] .'/includes/header.html.php';?>
<!--Main content-->
<div id="mainholder"> <!-- div so that page footer can have a minum height from the
  header -->
<h1><?php if(isset($pagetitle)) htmlout($pagetitle);?></h1>
<br>
<br>
<article>
    <h2></h2>
</article>
<?php
if (isset($servicecalls)) {
if (count ($servicecalls) > 0){
     foreach ($servicecalls as $servicecall) {
        echo '<a href="/servicecalls/?servicecall=' .$servicecall->ID .'">'
  .$servicecall->ServiceCallDescription .'</a>';
    }
}else echo 'No service Calls';

}

?>
<a href="/servicecalls/?new=true">Raise New Service Call</a>
</div> <!-- Main content end-->
<?php include $_SERVER['DOCUMENT_ROOT'] .'/includes/footer.html.php'; ?>

改变它

$results->fetch_array()

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM