Инициализировать объекты как массивы в PHP? - PullRequest
26 голосов
/ 16 ноября 2009

В PHP вы можете быстро инициализировать массивы значениями, используя следующие обозначения:

$array = array("name" => "member 1", array("name" => "member 1.1") ) ....

Есть ли способ сделать это для объектов STDClass? Я не знаю более короткого пути, чем тоскливый

$object = new STDClass();
$object->member1 = "hello, I'm 1";
$object->member1->member1 = "hello, I'm 1.1";
$object->member2 = "hello, I'm 2";

Ответы [ 8 ]

40 голосов
/ 16 ноября 2009

Вы можете использовать тип приведения:

$object = (object) array("name" => "member 1", array("name" => "member 1.1") );
25 голосов
/ 12 января 2013

Я также назвал Гамбо предпочтительным решением, но он предложил не совсем то, о чем спрашивали, что может привести к некоторой путанице в отношении того, почему member1o выглядит больше как member1a.

Чтобы убедиться, что это ясно сейчас, есть два способа (теперь 3 способа, начиная с 5.4), чтобы получить тот же stdClass в php.

  1. В соответствии с длинным или ручным подходом к вопросу:

    $object = new stdClass;
    $object->member1 = "hello, I'm 1";
    $object->member1o = new stdClass;
    $object->member1o->member1 = "hello, I'm 1o.1";
    $object->member2 = "hello, I'm 2";
    
  2. Укороченная или однострочная версия (расширенная для ясности) для приведения объекта из массива, по предложению аля Гамбо.

    $object = (object)array(
         'member1' => "hello, I'm 1",
         'member1o' => (object)array(
             'member1' => "hello, I'm 1o.1",
         ),
         'member2' => "hello, I'm 2",
    );
    
  3. PHP 5.4+ Стиль объявления укороченного массива

    $object = (object)[
         'member1' => "hello, I'm 1",
         'member1o' => (object)['member1' => "hello, I'm 1o.1"],
         'member2' => "hello, I'm 2",
    ];
    

И тот и другой даст одинаковый результат:

stdClass Object
(
    [member1] => hello, I'm 1
    [member1o] => stdClass Object
        (
            [member1] => hello, I'm 1o.1
        )

    [member2] => hello, I'm 2
)

NJoy!

6 голосов
/ 16 ноября 2009

Из сообщения, показывающего как приведение типа, так и использование рекурсивной функции для преобразования одно- и многомерных массивов в стандартный объект:

<?php
function arrayToObject($array) {
    if (!is_array($array)) {
        return $array;
    }

    $object = new stdClass();
    if (is_array($array) && count($array) > 0) {
        foreach ($array as $name=>$value) {
            $name = strtolower(trim($name));
            if (!empty($name)) {
                $object->$name = arrayToObject($value);
            }
        }
        return $object;
    }
    else {
        return FALSE;
    }
}

По сути, вы создаете функцию, которая принимает $array и выполняет итерацию по всем ее ключам и значениям. Он присваивает значения свойствам класса с помощью ключей.

Если значение является массивом, вы вызываете функцию снова (рекурсивно) и присваиваете ее выход в качестве значения.

Пример функции выше делает именно это; однако логика, вероятно, упорядочена немного иначе, чем вы, естественно, думаете о процессе.

5 голосов
/ 01 февраля 2015

Вы можете использовать:

$object = (object)[]; // shorter version of (object)array();

$object->foo = 'bar';
5 голосов
/ 16 ноября 2009

Вы можете попробовать:

function initStdClass($thing) {
    if (is_array($thing)) {
      return (object) array_map(__FUNCTION__, $thing);
    }
    return $thing;
}
4 голосов
/ 16 ноября 2009

Я использую класс, который я называю Dict:

class Dict {

    public function __construct($values = array()) {
        foreach($values as $k => $v) {
            $this->{$k} = $v;
        }
    }
}

Он также имеет функции для слияния с другими объектами и массивами, но это как бы выходит за рамки этого вопроса.

3 голосов
/ 08 мая 2017

из это ответ на аналогичный вопрос:

Начиная с PHP7 , у нас есть Анонимные классы , которые позволят вам расширить класс во время выполнения, включая установку дополнительных свойств:

$a = new class() extends MyObject {
    public $property1 = 1;
    public $property2 = 2;
};

echo $a->property1; // prints 1

Это не так кратко, как инициализатор для массива. Не уверен, что я бы использовал это. Но - это еще один вариант, который вы можете рассмотреть.

2 голосов
/ 28 сентября 2016

Другой вариант для преобразования deep - использовать json_encode + json_decode (по умолчанию он декодируется в stdClass). Таким образом, вам не придется повторять (object) приведение к каждому вложенному объекту.

$object = json_decode(json_encode(array(
     'member1' => "hello, I'm 1",
     'member1o' => array(
         'member1' => "hello, I'm 1o.1",
     ),
     'member2' => "hello, I'm 2",
)));

выход:

php > print_r($object);
stdClass Object
(
    [member1] => hello, I'm 1
    [member1o] => stdClass Object
        (
            [member1] => hello, I'm 1o.1
        )

    [member2] => hello, I'm 2
)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...