2009-10-10 2 views
21

내가 누락되었거나 PHP 5.x에서 암시하는 일반 객체 유형을 지원하지 않습니다.PHP 유형 힌트 : 배열 지원, 객체 NOT?

힌팅 객체가 지원되지 않는 동안 힌팅 배열이 지원된다는 것은 정말 이상한 일입니다.

나는 이런 식으로 뭔가를 싶습니다

function foo(object $o) 

을 우리가 그냥 같이 가능한 사용의

function foo(array $o) 

예 : 객체들 컬렉션 클래스의 방법을.

해결 방법 :이 같은 것을 모든 클래스에 의해 구현 된 인터페이스 "개체"를 사용하거나 제네릭 클래스 "개체"에서 모든 클래스를 확장하고 쓰기 : 그건 그냥 귀여운

function foo(Object $o) 

잘되지 않습니다.

작동하지 않는 타입 힌트로 stdClass 사용 : 타입 힌트 이후

Catchable fatal error: Argument 1 passed to c::add() must be an instance of stdClass, instance of b given

+1

힌트 유형에 콘크리트 유형을 사용하지 마십시오. 인터페이스를 사용하거나 오리 입력에 대해 읽으십시오. –

+0

구체적인 형식 경로를 걷는다면 is_object()를 사용하고 싶습니다. 그러나 그것은이 토론의 요점이 아닙니다. –

+5

보세요, PHP는 자바처럼 객체가 하나의 클래스에서 상속받지 않는 매우 모순 된 언어입니다. 실제로 일반적인 객체에 대한 유형 힌팅이 없다는 사실은 실제로 감독이지만,이 지점을지나 다른 이상한 것을 준비해야한다고 생각합니다. –

답변

6

는 아니, 그것은 할 수 없습니다 (구문이 유효 함을 의미하지 않음). 나는 아무것도 놓치지 않았다.

+0

에 대해 \ stdClass가 true가 아닙니다. 내 대답을 참조하십시오 –

7

클라이언트 코드가 API에 적응해야한다, 수용 인터페이스 솔루션은 바로 대해 같다. 그것에

봐이 방법 : yourMethod(array $input)하여 당신이 적용 exactly which native functions을 알고 yourMethod() 사용할 수 있습니다, yourMethod() 사용하는 배열을 제공합니다.

당신처럼 방법을 지정하는 경우

는 : yourSecondMethod(yourInterface $input) 당신은 또한 인터페이스 yourInterface 함께 규칙을 설정하는 조회 할 수있는 당신이 알고 있기 때문에 $input에 적용 할 수있는 방법/알 것입니다.

입력에 사용할 방법을 알 수있는 방법이 없기 때문에 개체를 수락하는 것은 잘못된 것 같습니다. 예 :

function foo(Object $o) { 
    return $o->thisMethodMayOrMayNotExist(); 
} 

+1

자식에 대해 아무런 메소드도 호출하지 않으며 해당 속성/특성을 사용하지 않는 (의사) 컨테이너로 작동 할 객체 컬렉션 클래스의 경우는 그렇지 않습니다. 변수를 알고있는 것은 객체이기 때문에 많은 네이티브 함수를 사용할 수 있으므로 실제로 요점을 보지 못합니다. –

+2

SplObjectStorage 또는 ArrayObject와 같은 유형 힌트를 사용하는 것은 어떻습니까? – chelmertz

+0

단순 컨테이너 오브젝트 – Kzqai

0

왜 대신 실제 클래스 이름을 암시 할 수있을 때 object을 암시 할 것이다 -이 훨씬 더 유용 할 것이다. 또한 당신도 int, float, bool, string 또는 resource을 암시 할 수 있음을 기억하십시오.

+3

왜 배열을 치고 싶습니까? 힌트를 얻을 수없는 다른 모든 유형을 기억하십시오 ... 모든 PHP 클래스가 내려지는 공통 기본 클래스가 없으므로 배열을 암시하는 것처럼 객체를 힌트 할 수있는 것이 좋습니다. 내 생각에,하지만 나는 이걸로 혼자 있을지 몰라. –

+1

일반 객체에 대한 유형 힌팅을위한 인스턴스를 생각할 수 없기 때문에 필요가 없다는 것을 의미하지는 않습니다. Rikki의 설명은 완벽한 예입니다. int, float, bool, string 및 resource에 대한 힌트를 입력 할 수 없다는 사실 역시 감시 대상입니다. 명시 적으로 인수를 정수로만 제한하려는 경우가 많이있었습니다. 그래서 대신에, 나는 "is_int"난센스 호출을 사용하여 붙어 있습니다. –

6

나는 당신의 고통을 느끼지만, 나도 그 일을하는 방법을 찾을 수 없습니다.

많은 다른 포스터가 말한 것처럼, '개체'형식 힌트를 사용하는 것이 좋습니다. 그들은 단지 그것을 요구하는 시나리오를 고려하지 않았습니다.

나는 반사 API 몇 가지 일을하려고하고, 그 때문에 나는 내 함수에 전달되는 클래스 상관하지 않습니다. 내가 신경 쓰는 건 그것이 대상이라는 것이다. int, float, string 또는 array는 필요 없습니다. 나는 물건이 필요해. 리플렉션이 PHP의 일부가되었으므로 객체 유형 힌팅을 사용하는 것이 타당합니다.

2

는 여기에 내가 레코드 잠금을 구현하는 클래스를 생성 한

...이 필요한 또 다른 예입니다. 레코드는 다양한 오브젝트 유형 중 하나입니다. 잠금 클래스에는 객체 (잠겨있는 객체)가 필요하지만 객체의 유형을 신경 쓰지 않는 여러 메소드가 있습니다.

예.

public static function lockRecord($record, User $user, $timeout=null) 
{ 
    if(!is_object($record)) throw new \InvalidException("Argument 1 must be an object."); 

    $lock=new Lock(); 
    $lock->setRecord($record); 
    $lock->setUser($user); 
    $lock->setTimeout($timeout); 
    $lock->activate(); 
    return($lock); 
} 

내 솔루션 (is_object 사용) 및 예외가 발생하는 것을 볼 수 있습니다,하지만 난 지금까지 오히려 형 대신 힌트와 함께 할 수있을 것입니다.

세계의 끝이 아니라, 좋아,하지만 나는 수치 스럽다고 생각합니다.

4

개체를 형 변환 할 때 "개체"라고 말할 수는 없습니다 ... 원하는 개체를 정의해야합니다. 에서

: 당신이 그것을 필요로 할 경우 http://php.net/manual/en/language.oop5.typehinting.php

class MyClass 
{ 
    /** 
    * A test function 
    * 
    * First parameter must be an object of type OtherClass 
    */ 
    public function test(OtherClass $otherclass) { 
     echo $otherclass->var; 
    } 


    /** 
    * Another test function 
    * 
    * First parameter must be an array 
    */ 
    public function test_array(array $input_array) { 
     print_r($input_array); 
    } 
} 

// Another example class 
class OtherClass { 
    public $var = 'Hello World'; 
} 
0
public static function cloneObject($source) 
{ 
    if ($source === null) 
    { 
     return null; 
    } 

    return unserialize(serialize($source)); 
} 

이다.

+4

답변의 품질을 향상 시키려면 게시물로 인해 문제가 해결되는 방법/이유를 포함 시키십시오. –

3

이것을 적용하는 가장 좋은 방법은 Object이라는 축퇴 인터페이스를 만드는 것입니다. 퇴화 된 인터페이스는 정의 된 메소드가 없음을 의미합니다.

interface Object { 

    // leave blank 

} 

그런 다음 기본 클래스에서 Object을 구현할 수 있습니다. 당신이

function myFunc (Object $obj); 

myFunc($someBase); 

에 원하는대로

class SomeBase implements Object { 

    // your implementation 

} 

당신은 지금 당신이 당신의 Object 인터페이스를 상속 개체를 전달하면, 이러한 유형의 힌트가 전달합니다 함수를 호출 할 수 있습니다. 배열, int, string 등을 전달하면 형식 힌트가 실패합니다.

+0

불행히도 이것은 아마도 PHP에서 가장 가까이에있을 것입니다.하지만 만드는 모든 클래스가'Object' 인터페이스를 구현해야한다는 것을 의미합니다. 이것은 매우 단순한 무언가에 대한 오버 헤드가 많습니다. Ahhhhh, PHP .. – mAAdhaTTah

+3

OP가 이미이 전략을 가능한 해결 방법으로 질문했습니다. 이렇게하면 타사 라이브러리에 정의 된 내장 클래스 나 클래스 인스턴스를 전달할 수 없습니다. –

1

PHP의 객체는 다른 OOP 언어와 마찬가지로 일부 StdClass 또는 Object의 하위 클래스가 아닙니다. 따라서 객체를 암시하는 유형은 없습니다. 하지만 때로는 객체가 전달되고 있는지 확인하기를 원하기 때문에 문제를 수동으로 제기하는 것이 유일한 방법이라고 생각하기 때문에 귀하의 요점을 보게됩니다. PHP 5.4로

public function yourFunction($object){ 
    if(is_object($object)){ 
     //TODO: do something 
    }else{ 
     throw new InvalidArgumentException; 
    } 
} 

또한 타입 힌트 호출있다. PHP 설명서 참조 http://php.net/manual/en/language.types.callable.php