Как определить пустой объект в PHP

С Новым массивом я делаю это:

$aVal = array();

$aVal[key1][var1] = "something";
$aVal[key1][var2] = "something else";

есть ли аналогичный синтаксис для объекта

(object)$oVal = "";

$oVal->key1->var1 = "something";
$oVal->key1->var2 = "something else";

16 ответов


$x = new stdClass();

на комментарий в руководстве подводит итог:

stdClass является объектом PHP по умолчанию. stdClass не имеет свойств, методов или родитель. Он не поддерживает магию методы и не реализует интерфейсов.

при приведении скаляра или массива как Объект, вы получаете экземпляр stdClass. Вы можете использовать stdClass всякий раз, когда вам нужен универсальный объект пример.


стандартный способ создания "пустого" объекта:

$oVal = new stdClass();

но, с PHP >= 5.4, I лично предпочитаете использовать:

$oVal = (object)[];

это короче, и я лично считаю это более ясным, потому что stdClass может вводить в заблуждение начинающих программистов (т. е. "Эй, я хочу объект, а не класс!"...).

то же самое с PHP

$oVal = (object) array();

(object)[] эквивалентно new stdClass().

см. руководство по PHP (здесь):

stdClass: создано путем типизации объекта.

и (здесь):

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


запомните это empty ($oVal) возвращает false, как сказал @PaulP:

объекты без свойств больше не считаются пустыми.

относительно вашего примера, если вы пишете:

$oVal = new stdClass();
$oVal->key1->var1 = "something"; // PHP creates  a Warning here
$oVal->key1->var2 = "something else";

PHP создает следующее предупреждение, неявно создавая свойство key1 (сам объект)

предупреждение: создание объекта по умолчанию из пустого значения

это может быть проблемой, если ваш конфигурация (см. уровень отчетов об ошибках) показывает это предупреждение в браузере. Это еще одна целая тема, но быстрый и грязный подход может использовать оператор контроля ошибок (@) игнорировать предупреждение:

$oVal = new stdClass();
@$oVal->key1->var1 = "something"; // the warning is ignored thanks to @
$oVal->key1->var2 = "something else";

Я хочу отметить, что в PHP нет такой вещи, как пустой объект в смысле:

$obj = new stdClass();
var_dump(empty($obj)); // bool(false)

но, конечно, $obj будет пустым.

С другой стороны, пустой массив означает пустой в обоих случаях

$arr = array();
var_dump(empty($arr));

цитата из функции changelog пустой

объекты без свойств больше не считаются пустыми.


php.net сказал это лучше всего:

$new_empty_object = new stdClass();

мне нравится, как легко создавать объекты анонимного типа в JavaScript:

//JavaScript
var myObj = {
    foo: "Foo value",
    bar: "Bar value"
};
console.log(myObj.foo); //Output: Foo value

поэтому я всегда стараюсь писать такие объекты в PHP как javascript делает:

//PHP >= 5.4
$myObj = (object) [
    "foo" => "Foo value",
    "bar" => "Bar value"
];

//PHP < 5.4
$myObj = (object) array(
    "foo" => "Foo value",
    "bar" => "Bar value"
);

echo $myObj->foo; //Output: Foo value

но поскольку это в основном массив, вы не можете делать такие вещи, как назначение анонимных функций свойству, как js:

//JavaScript
var myObj = {
    foo: "Foo value",
    bar: function(greeting) {
        return greeting + " bar";
    }
};
console.log(myObj.bar("Hello")); //Output: Hello bar

//PHP >= 5.4
$myObj = (object) [
    "foo" => "Foo value",
    "bar" => function($greeting) {
        return $greeting . " bar";
    }
];
var_dump($myObj->bar("Hello")); //Throw 'undefined function' error
var_dump($myObj->bar); //Output: "object(Closure)"

Ну, вы можете это сделать, но IMO не практично / чисто:

$barFunc = $myObj->bar;
echo $barFunc("Hello"); //Output: Hello bar

кроме того, с помощью этого synthax вы можете найти некоторые забавные сюрпризы, но работает отлично в большинстве случаев.


В дополнение к ответу zombat, если вы продолжаете забывать stdClass

   function object(){

        return new stdClass();

    }

Теперь вы можете сделать:

$str='';
$array=array();
$object=object();

доступ к данным в stdClass аналогичным образом вы с массивом asociative просто использовать синтаксис {$переменная}.

$myObj = new stdClass;
$myObj->Prop1 = "Something";
$myObj->Prop2 = "Something else";

// then to acces it directly

echo $myObj->{'Prop1'};
echo $myObj->{'Prop2'};

// or what you may want

echo $myObj->{$myStringVar};

можно использовать new stdClass() (рекомендуется):

$obj_a = new stdClass();
$obj_a->name = "John";
print_r($obj_a);

// outputs:
// stdClass Object ( [name] => John ) 

или вы можете преобразовать пустой массив в объект, который создает новый пустой экземпляр встроенного класса stdClass:

$obj_b = (object) [];
$obj_b->name = "John";
print_r($obj_b);

// outputs: 
// stdClass Object ( [name] => John )  

или вы можете преобразовать null значение для объекта, который создает новый пустой экземпляр встроенного класса stdClass:

$obj_c = (object) null;
$obj_c->name = "John";
print($obj_c);

// outputs:
// stdClass Object ( [name] => John ) 

вы также можете попробовать этот способ.

<?php
     $obj = json_decode("{}"); 
     var_dump($obj);
?>

выход:

object(stdClass)#1 (0) { }

как указывали другие, вы можете использовать stdClass. Однако я думаю, что это чище без (), например:

$obj = new stdClass;
судя по вопросу, похоже, что вы действительно хотите, чтобы иметь возможность добавлять свойства к объекту на лету. Вам не нужно использовать stdClass для этого, хотя вы можете. Действительно, Вы можете использовать любой класс. Просто создайте экземпляр объекта любого класса и начните задавать свойства. Мне нравится создавать свой собственный класс, имя которого просто o с некоторыми базовыми расширенная функциональность, которую я люблю использовать в этих случаях и хороша для расширения из других классов. В основном это мой собственный базовый класс объектов. Мне также нравится иметь функцию с простым именем o (). Вот так:
class o {
  // some custom shared magic, constructor, properties, or methods here
}

function o() {
  return new o;
}

Если вам не нравится иметь свой собственный базовый тип объекта, вы можете просто вернуть o() Новый stdClass. Одним из преимуществ является то, что o легче запомнить, чем stdClass, и короче, независимо от того, используете ли вы его в качестве имени класса, имени функции или обоих. Даже если у тебя нет любой код внутри вашего класса o все равно легче запомнить, чем неуклюже заглавный и названный stdClass (который может вызвать идею "класса заболеваний, передаваемых половым путем"). Если вы настроите класс o, вы можете найти использование для функции o() вместо синтаксиса конструктора. Это нормальная функция, которая возвращает значение, которое менее ограничено, чем конструктор. Например, имя функции может быть передано в виде строки функции, которая принимает вызываемый параметр. Функция также поддерживает. Таким образом, вы можете сделать что-то вроде: $result= o ($internal_value) - >some_operation_or_conversion_on_this_value ();

Это отличный старт для базового "языка" для создания других языковых слоев, причем верхний слой написан в полном внутреннем DSL. Это похоже на стиль разработки lisp, и PHP поддерживает его лучше, чем большинство людей понимают. Я понимаю, что это немного касательная к вопросу, но вопрос касается того, что я думаю, является основой для полного использования мощности PHP.


Если вы хотите создать объект (например, в javascript) с динамическими свойствами, не получая предупреждения о неопределенном свойстве.

class stdClass {

public function __construct(array $arguments = array()) {
    if (!empty($arguments)) {
        foreach ($arguments as $property => $argument) {
            if(is_numeric($property)):
                $this->{$argument} = null;
            else:
                $this->{$property} = $argument;
            endif;
        }
    }
}

public function __call($method, $arguments) {
    $arguments = array_merge(array("stdObject" => $this), $arguments); // Note: method argument 0 will always referred to the main class ($this).
    if (isset($this->{$method}) && is_callable($this->{$method})) {
        return call_user_func_array($this->{$method}, $arguments);
    } else {
        throw new Exception("Fatal error: Call to undefined method stdObject::{$method}()");
    }
}

public function __get($name){
    if(property_exists($this, $name)):
        return $this->{$name};
    else:
        return $this->{$name} = null;
    endif;
}

public function __set($name, $value) {
    $this->{$name} = $value;
}

}

$obj1 = new stdClass(['property1','property2'=>'value']); //assign default property
echo $obj1->property1;//null
echo $obj1->property2;//value

$obj2 = new stdClass();//without properties set
echo $obj2->property1;//null

мы можем просто создать пустой объект, используя этот метод:

$object = new ObjectClass();

например:

class ObjectClass
{
    // Something goes here
}

$object = new ObjectClass();

теперь у нас есть переменная $object что это ObjectClass но пустой. Если он содержит функцию __construct(), тогда он может быть не пустым.

Я знаю, это старый вопрос, но кажется, что некоторые люди забывают о конструкторах.


Если вы не хотите этого делать:

$myObj = new stdClass();
$myObj->key_1 = 'Hello';
$myObj->key_2 = 'Dolly';

вы можете использовать один из следующих:

PHP >=5.4

$myObj = (object) [
    'key_1' => 'Hello',
    'key_3' => 'Dolly',
];

PHP

$myObj = (object) array(
    'key_1' => 'Hello',
    'key_3' => 'Dolly',
);

используйте универсальный объект и сопоставьте ему пары значений ключей.

$oVal = new stdClass();
$oVal->key = $value

или бросить массив в объект

$aVal = array( 'key'=>'value' );
$oVal = (object) $aVal;

вот пример с итерацией:

<?php
$colors = (object)[];
$colors->red = "#F00";
$colors->slateblue = "#6A5ACD";
$colors->orange = "#FFA500";

foreach ($colors as $key => $value) : ?>
    <p style="background-color:<?= $value ?>">
        <?= $key ?> -> <?= $value ?>
    </p>
<?php endforeach; ?>

У вас есть эта плохая, но полезная техника:

$var = json_decode(json_encode([]), FALSE);