PHP에서 익명 객체 만들기


141

아시다시피 아래 코드와 같이 JavaScript로 익명 객체를 만드는 것은 쉽습니다.

var object = { 
    p : "value", 
    p1 : [ "john", "johnny" ]
};

alert(object.p1[1]);

산출:

an alert is raised with value "johnny"

이 같은 기술을 PHP에 적용 할 수 있습니까? PHP에서 익명 객체를 만들 수 있습니까?


1
참고 : 이것은 오래된 질문이므로 허용되는 답변이 오래되었습니다. 이 기능은 이제 PHP 7에 추가되었습니다. @ Rizier123의 아래 답변을 참조하십시오.
Simba

@ Simba-지적 해 주셔서 감사합니다. 이 페이지의 다음 페이지에 StackOverflow에 대한 답변을 게시 하시겠습니까?
Sujit Agarwal

1
필요가 없습니다. 이미이 정보에 대한 답변이 있습니다 (@ Rizier123의 아래 참조).
Simba

답변:


40

몇 년이 지났지 만 정보를 최신 상태로 유지해야한다고 생각합니다!

PHP 7부터는 익명 클래스를 만들 수 있으므로 다음과 같은 작업을 수행 할 수 있습니다.

<?php

    class Foo {}
    $child = new class extends Foo {};

    var_dump($child instanceof Foo); // true

?>

이에 대한 자세한 내용 은 매뉴얼을 참조하십시오

그러나 JavaScript와 JavaScript가 얼마나 유사한 지 잘 모르겠으므로 JavaScript와 PHP의 익명 클래스에는 약간의 차이가있을 수 있습니다.


@risyasin 감사합니다, 답변을 업데이트하고 수동 링크를 넣습니다.
Rizier123

php7의 최신 변경 사항에 따라 답을 올바른 것으로 표시하십시오. 감사합니다 @ Rizier123
Sujit Agarwal

3
이것은 흥미롭지 만 OP는 클래스를 만들지 않고 다양한 멤버로 객체를 초기화하는 편리한 방법을 요구했기 때문에 실제로 문제를 해결하지는 못합니다. PHP의 익명 클래스를 사용하여 사용할 수 있는지 확실하지 않으며 가능한 경우 방법을 설명하지 않았습니다.
amh15

228

"익명"은 객체에 대해 말할 때 올바른 용어가 아닙니다. "익명 타입의 객체"라고 말하는 것이 좋지만 PHP에는 적용되지 않습니다.

PHP의 모든 객체에는 클래스가 있습니다. "default"클래스는 다음 stdClass과 같은 방식으로 객체를 만들 수 있습니다.

$obj = new stdClass;
$obj->aProperty = 'value';

보다 편리한 구문을 위해 배열을 객체캐스트하는 이점을 활용할 수도 있습니다 .

$obj = (object)array('aProperty' => 'value');
print_r($obj);

그러나, 객체 배열을 캐스팅하는 것은 유효한 PHP 변수 이름없는 그 배열 키 "흥미로운"결과를 산출 할 가능성이 있음을 통보 - 예를 들어, 여기 내 대답이 키가 숫자로 시작하면 어떻게되는지 보여줍니다.


1
여러 값을 가진 배열을 푸시 할 수 있습니까?
Sujit Agarwal

2
@CodingFreak : 할 수 있지만 : 배열에 하위 배열이 포함되어 있고 객체로 객체를 원할 경우 모든 객체를 명시 적으로 객체로 캐스팅해야합니다.
Jon

21

네 가능합니다! 이 간단한 PHP Anonymous Object 클래스를 사용합니다. 작동 방식 :

// define by passing in constructor
$anonim_obj = new AnObj(array(
    "foo" => function() { echo "foo"; }, 
    "bar" => function($bar) { echo $bar; } 
));

$anonim_obj->foo(); // prints "foo"
$anonim_obj->bar("hello, world"); // prints "hello, world"

// define at runtime
$anonim_obj->zoo = function() { echo "zoo"; };
$anonim_obj->zoo(); // prints "zoo"

// mimic self 
$anonim_obj->prop = "abc";
$anonim_obj->propMethod = function() use($anonim_obj) {
    echo $anonim_obj->prop; 
};
$anonim_obj->propMethod(); // prints "abc"

물론이 객체는 AnObj클래스 의 인스턴스 이므로 실제로는 익명이 아니지만 JavaScript처럼 메소드를 즉석에서 정의 할 수 있습니다.


create_function 을 사용 하여 익명 함수를 에뮬레이트 할 수 있습니다 .
Mihailoff

그는 단지 일부 값으로 stdClass 객체를 초기화하는 깔끔한 방법을 원했다고 생각합니다. 당신의 접근 방식으로 그렇게 할 수 있습니까?
amh15

18

최근까지 이것은 객체를 즉석에서 생성 한 방법입니다.

$someObj = json_decode("{}");

그때:

$someObj->someProperty = someValue;

그러나 지금 나는 다음과 같이 간다.

$someObj = (object)[];

그런 다음 이전처럼 :

$someObj->someProperty = someValue;

물론 이미 속성과 값을 알고 있다면 언급 한대로 내부에서 설정할 수 있습니다.

$someObj = (object)['prop1' => 'value1','prop2' => 'value2'];

NB : 어떤 버전의 PHP가 작동하는지 잘 모르겠 기 때문에이를 염두에 두어야합니다. 그러나 첫 번째 접근 방식 (제작시 설정할 속성이없는 경우에도 짧음)은 json_encode / json_decode가있는 모든 버전에서 작동해야한다고 생각합니다.


1
$ someObj = new \ stdClass ()와 다른 점은 무엇입니까?
JamesNZ

9

배열을 객체로 변환하십시오 (그러나 이것은 하위 자식에게는 재귀 적이 지 않습니다).

$obj = (object)  ['myProp' => 'myVal'];

7

JavaScript를 모방하려는 경우 클래스를 만들면 Object동일한 동작을 얻을 수 있습니다. 물론 이것은 더 이상 익명이 아니지만 작동합니다.

<?php 
class Object { 
    function __construct( ) { 
        $n = func_num_args( ) ; 
        for ( $i = 0 ; $i < $n ; $i += 2 ) { 
            $this->{func_get_arg($i)} = func_get_arg($i + 1) ; 
        } 
    } 
} 

$o = new Object( 
    'aProperty', 'value', 
    'anotherProperty', array('element 1', 'element 2')) ; 
echo $o->anotherProperty[1];
?>

그러면 요소 2 가 출력됩니다 . 이것은에서 도난당한 클래스와 객체 : PHP에 대한 코멘트 .


3

익명 클래스에 대한 지원은 PHP 7.0부터 제공되었으며 질문에 제공된 JavaScript 예제와 가장 유사합니다.

<?php
$object = new class {
    var $p = "value";
    var $p1 = ["john", "johnny"];
};

echo $object->p1[1];

속성에 대한 가시성 선언은 생략 할 수 없습니다 (방금 var보다 짧기 때문에 방금 사용 했습니다 public.)

JavaScript와 마찬가지로 클래스의 메소드를 정의 할 수도 있습니다.

<?php
$object = new class {
    var $p = "value";
    var $p1 = ["john", "johnny"];
    function foo() {return $this->p;}
};

echo $object->foo();

1

PHP 문서에서 몇 가지 예가 더 있습니다 :

<?php

$obj1 = new \stdClass; // Instantiate stdClass object
$obj2 = new class{}; // Instantiate anonymous class
$obj3 = (object)[]; // Cast empty array to object

var_dump($obj1); // object(stdClass)#1 (0) {}
var_dump($obj2); // object(class@anonymous)#2 (0) {}
var_dump($obj3); // object(stdClass)#3 (0) {}

?>

$ obj1과 $ obj3은 같은 유형이지만 $ obj1! == $ obj3입니다. 또한 세 가지 모두 json_encode ()를 간단한 JS 객체 {}로 보냅니다.

<?php

echo json_encode([
    new \stdClass,
    new class{},
    (object)[],
]);

?>

출력 :

[{},{},{}]

https://www.php.net/manual/en/language.types.object.php


0

속성으로 값을 설정하지 않은 경우 정의되지 않은 속성의 경고를받지 않고 동적 속성으로 객체 (예 : 자바 스크립트와 같이)를 만들려면

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

0

PHP의 경우에도 동일한 기술을 적용 할 수 있습니까?

자바 스크립트는 객체의 프로토 타입 / 직접 선언을 사용하기 때문에 PHP (및 다른 많은 OO 언어)에서 객체는 클래스에서만 만들 수 있습니다.

따라서 질문은 익명 클래스를 만들 수 있습니다.

다시 대답은 '아니오'입니다. 클래스를 참조하지 않고 클래스를 어떻게 인스턴스화 하시겠습니까?


익명 클래스의 인스턴스를 생성하기 위해 이름이 필요하지 않습니다. 자바 : Object var = new Object() { ... };-C ++ :class { ... } var;
TheOperator

1
PHP에서 익명 클래스를 만들 수 있습니다.
Victor

0

재귀 객체를 원하는 사람의 경우 :

$o = (object) array(
    'foo' => (object) array(
        'sub' => '...'
    )
);

echo $o->foo->sub;

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.