배열 대신 객체를 반환하는 이유는 무엇입니까?


84

저는 워드 프레스에서 많은 작업을하는데 배열보다 객체를 반환하는 함수가 훨씬 더 많다는 것을 알게되었습니다. 특별히 배열을 요청하지 않는 한 데이터베이스 결과는 객체로 반환됩니다. 오류는 객체로 반환됩니다. WordPress 외부에서 대부분의 API는 배열 대신 객체를 제공합니다.

내 질문은 왜 배열 대신 객체를 사용합니까? 대부분의 경우 그다지 중요하지 않지만 어떤 경우에는 처리하는 것뿐만 아니라 머리를 감싸는 것이 더 어려운 물체를 찾습니다. 객체를 사용하는 성능상의 이유가 있습니까?

저는 독학으로 PHP 프로그래머입니다. 저는 인문학 학위를 받았습니다. 컴퓨터 과학의 근본적인 측면을 놓치고 있다면 저를 용서하십시오. ;)


5
나는 객체 의 단점 과 관련하여 이것에 대해 궁금 합니다 (적어도 키 => 값 데이터 저장 / 반환과 관련하여) 사용할 수 count()없거나 array_*()기능 을 사용할 수 없습니다 . 아무도 그것을 언급하지 않는 것 같습니까, 아니면 내가 뭔가를 놓치고 있습니까?
Wesley Murch 2011

8
Countable 또는 Iterator 인터페이스를 구현하여 개체를 계산 및 반복 가능하게 만들 수 있습니다. php.net/manual/en/book.spl.php 도 확인하십시오 .
simshaun jul.

SPL이 설치되어 있고 개체 클래스에 대해 계산 가능한 인터페이스를 구현 한 count()경우 개체를 호출 할 수 있습니다 .
SE에서 떠나는 사람이 없습니다.

2
대부분의 경우 배열은 개체 모음이나 배열로 쉽게 에뮬레이션 할 수없는 일종의 모음을 반환하지 않기 때문에 의미가 없습니다. 다른 값의 시퀀스 만 있고 추가 의미 체계가 연결되지 않은 경우, 제발 배열을 반환합니다.하지만 그런 경우는 드물다는 것을 알게 될 것입니다.

8
@delnan 및 기타 : @Dennis는 일반 (정수 인덱스) 배열이 아닌 연관 배열 (일명 사전, 일명지도) 에 대해 이야기하고 있습니다. 이들은 PHP의 핵심 기능이며 동적 클래스 ( stdClass) 와 거의 동일한 목적을 제공 합니다. 나는 확실하지 "OOP에서 주로 작업을 프로그래머가 객체를 사용하는 의미 선호하기 때문에"이 질문이 아닌 대답을 가지고있어
대니 Pflughoeft - BlueRaja

답변:


62

내가 일반적으로 객체를 선호하는 이유는 다음과 같습니다.

  • 객체는 데이터뿐만 아니라 기능도 포함합니다.
  • 객체에는 (대부분의 경우) 미리 정의 된 구조가 있습니다. 이것은 API 설계에 매우 유용합니다. 또한 속성을 public, protected 또는 private으로 설정할 수 있습니다.
  • 객체는 객체 지향 개발에 더 적합합니다.
  • 대부분의 IDE에서 자동 완성은 개체에 대해서만 작동합니다.

읽어야 할 것이 있습니다.


3
첫 번째 링크가 좋지 않은 것 같습니까? 나는 그것이 작동하지만 다른 aritcle에 소요 의미
지오

24

이것은 아마도 몇 년 동안 대규모 소프트웨어 프로젝트에서 작업하기 전까지는 깊이 이해하지 못할 것입니다. 많은 새로운 컴퓨터 과학 전공자들이 모든 올바른 단어 (캡슐화, 데이터 기능 및 유지 관리 용이성)로 답을 제공하지만 그 모든 것이 왜 좋은지 이해하는 사람은 거의 없습니다.

몇 가지 예를 살펴 보겠습니다.

  • 배열이 반환 된 경우 모든 값을 미리 계산하거나 더 복잡한 값을 작성할 수있는 많은 작은 값을 반환해야합니다.

WordPress 게시물 목록을 반환하는 API 메서드를 생각해보십시오. 이 게시물에는 모두 저자가 있고, 저자는 이름, 이메일 주소, 심지어 약력이있는 프로필도 있습니다.

배열의 모든 게시물을 반환하는 경우 게시물 ID의 배열을 반환하도록 제한해야합니다.

[233, 41, 204, 111]

또는 다음과 같은 대규모 배열을 반환합니다.

[ title: 'somePost', body: 'blah blah', 'author': ['name': 'billy', 'email': 'bill@bill.com', 'profile': ['interests': ['interest1', 'interest2', ...], 'bio': 'info...']] ]
[id: '2', .....]]

ID 목록을 반환하는 첫 번째 경우는 해당 게시물에 대한 정보를 얻기 위해 각 ID에 대해 API 호출을해야하기 때문에별로 도움이되지 않습니다.

두 번째 경우는 90 %의 시간이 필요한 것보다 더 많은 정보를 가져오고 더 많은 작업을 수행합니다 (특히 이러한 필드 중 하나라도 구축하기가 매우 복잡한 경우).

반면에 객체는 필요한 모든 정보에 대한 액세스를 제공 할 수 있지만 실제로 해당 정보를 아직 가져 오지 않았습니다. 객체를 사용할 때 필드의 값을 결정하는 것은 느리게 (즉, 값이 필요하고 사전에 필요하지 않은 경우) 수행 될 수 있습니다.

  • 어레이는 의도 한 것보다 더 많은 데이터와 기능을 노출합니다.

반환되는 대규모 배열의 예로 돌아갑니다. 이제 누군가는 포스트 배열 내의 각 값을 반복하고 인쇄하는 애플리케이션을 빌드 할 수 있습니다. 해당 포스트 배열에 하나의 추가 요소 만 추가하도록 API가 업데이트되면 응용 프로그램 코드가 중단 될 것입니다. 왜냐하면 아마 안될 새 필드를 인쇄하기 때문입니다. API가 반환 한 포스트 배열의 항목 순서가 변경되면 애플리케이션 코드도 손상됩니다. 따라서 배열을 반환하면 개체가 만들지 않을 모든 종류의 가능한 종속성이 생성됩니다.

  • 기능성

객체는 유용한 기능을 제공 할 수 있도록 내부에 정보를 보유 할 수 있습니다. 예를 들어, post 객체는 이전 또는 다음 게시물을 반환 할만큼 똑똑 할 수 있습니다. 어레이는 당신을 위해 그렇게 할 수 없습니다.

  • 적응성

위에서 언급 한 개체의 모든 이점은보다 유연한 시스템을 만드는 데 도움이됩니다.


10

내 질문은 왜 배열 대신 객체를 사용합니까?

아마도 두 가지 이유가 있습니다.

  • WordPress는 꽤 오래되었습니다.
  • 대부분의 경우 어레이가 더 빠르고 메모리를 덜 사용합니다.
  • 직렬화가 더 쉬움

객체를 사용하는 성능상의 이유가 있습니까?

아니요.하지만 다음과 같은 많은 다른 좋은 이유가 있습니다.

  • 객체 (메서드, 클로저 등)에 로직을 저장할 수 있습니다.
  • 인터페이스를 사용하여 객체 구조를 강제 할 수 있습니다.
  • IDE에서 더 나은 자동 완성
  • 정의되지 않은 배열 키에 대한 알림을받지 못합니다.
  • 결국 모든 객체를 배열로 쉽게 변환 할 수 있습니다.

OOP ! = AOP :)

(예를 들어 Ruby에서는 모든 것이 객체입니다. PHP는 이전에 절차 / 스크립팅 언어였습니다.)


7

WordPress (및 상당량의 다른 PHP 응용 프로그램)는 기술적 이유가 아니라 개념적 이유로 배열보다는 객체를 사용합니다.

객체 (stdClass의 인스턴스 일지라도)는 하나의 표현입니다. WordPress에서 게시물, 댓글 또는 사용자 일 수 있습니다. 반면에 배열은 사물의 모음입니다. (예 : 게시물 목록)

역사적으로 PHP는 훌륭한 객체 지원이 없었기 때문에 배열은 초기에 상당히 강력 해졌습니다. (예를 들어, 제로 인덱스가 아닌 임의의 키를 가질 수있는 기능.) PHP 5에서 사용 가능한 객체 지원을 통해 개발자는 이제 배열 또는 객체를 키-값 저장소로 사용할 수 있습니다. 개인적으로 저는 객체와 배열이 제공하는 '엔티티'와 '컬렉션'의 구문 차이를 좋아하기 때문에 WordPress 접근 방식을 선호합니다.


5

내 질문은 왜 (Wordpress) 배열 대신 객체를 사용합니까?

정말 좋은 질문이고 대답하기 쉽지 않습니다. stdClass기본적으로 레코드를 stdClass개체 로 반환하는 데이터베이스 클래스를 사용하기 때문에 Wordpress에서 개체 를 사용하는 것이 일반적이라고 가정 할 수 있습니다 . 그들은 그것에 익숙해졌고 (8 년 이상) 그게 다입니다. 나는 단순한 사실 뒤에 더 많은 생각이 있다고 생각하지 않습니다.

연관 배열을위한 문법 설탕 - 지브 수라 스키 표준 개체에 대한 PHP 이후 3

  • stdClass객체는 배열보다 낫지 않습니다. 그들은 거의 동일합니다. 그것은 언어의 역사적 이유와 stdClass객체가 실제로 제한되어 있으며 실제로는 매우 기본적인 의미에서 일종의 가치 객체 일뿐 입니다.
  • stdClass객체는 항목 당 배열이 수행하는 것처럼 구성원의 값을 저장합니다. 그리고 그게 다야.
  • 오직 PHP 광들만 stdClass이 개인 멤버로 객체 를 생성 할 수 있습니다 . 그렇게하면 많은 이점이 없습니다.
  • stdClass객체에는 메소드 / 함수가 없습니다. 따라서 Wordpress에서는 사용하지 않습니다.
  • 와 비교할 때 array목록 또는 반 구조화 된 데이터를 처리하는 데 훨씬 덜 유용한 기능이 있습니다.

그러나 배열에 익숙하다면 다음을 캐스팅하십시오.

$array = (array) $object;

그리고 이전에 객체였던 데이터에 배열로 액세스 할 수 있습니다. 또는 다른 방식으로 좋아합니다.

$object = (object) $array;

숫자와 같은 유효하지 않은 멤버 이름 만 삭제됩니다. 그러니 조심하세요. 그러나 나는 당신이 큰 그림을 얻는다고 생각합니다 stdClass. 배열과 객체에 관한 한 큰 차이는 없습니다 .

관련 :


4
  1. 그런 식으로 코드가 더 멋지게 보입니다.
  2. 참조로 전달되는 객체
  3. 객체는 배열보다 더 강력한 유형이므로 오류가 발생하기 쉽습니다 (또는 존재하지 않는 구성원을 사용하려고 할 때 의미있는 오류 메시지를 표시 함).
  4. 오늘날의 모든 IDE에는 자동 완성 기능이 있으므로 정의 된 개체로 작업 할 때 IDE가 많은 작업을 수행하고 작업 속도를 높입니다.
  5. 논리 데이터를 동일한 상자에 쉽게 캡슐화합니다 . 여기서 배열을 사용하면 데이터를 배열에 저장 한 다음 다른 함수를 사용하여 처리합니다.
  6. 상속, 기능이 거의 비슷하지 않은 유사한 배열이있는 경우 개체를 사용하려면 더 많은 코드를 복제해야합니다.

아마도 내가 생각했던 이유가 더있을 것입니다.


"# Objects pass by reference": 틀 렸습니다. 객체는 PHP 변수 참조로 전달되지 않습니다. 그들은하지 않았습니다.
hakre

@hakre-php4에 있습니까? 또는 당신이 의미하는 것을 자세히 설명하십시오.
Itay Moav -Malimovka 2011

워드 프레스는 최근까지 PHP 4가 아니었지만 PHP 4 또는 PHP 5에서는 객체가 참조로 전달되지 않습니다. "자주 언급되는 PHP5 OOP의 핵심 포인트 중 하나는"객체는 기본적으로 참조에 의해 전달됩니다. " . 이것은 완전히 사실이 아닙니다.이 섹션에서는 몇 가지 예를 사용하여 일반적인 생각을 바로 잡습니다. " 개체 및 참고 자료
hakre 2011-07-20

@hakre-당신이 의미하는 바를 알지만 모든 목적을 위해 언어는 참조 만 전달하는 것처럼 작동합니다.
Itay Moav -Malimovka 2011

4

객체는 배열보다 훨씬 강력합니다. 클래스의 인스턴스 인 각 개체에는 함수가 연결될 수 있습니다. 처리가 필요한 데이터가있는 경우 처리를 수행하는 함수가 필요합니다. 배열을 사용하면 해당 배열에서 해당 함수를 호출해야하므로 논리를 데이터에 직접 연결해야합니다. 개체를 사용하면이 연결이 이미 완료되었으며 더 이상 신경을 쓸 필요가 없습니다.

또한 정보 은닉의 OO 원칙을 고려해야합니다. 데이터베이스에서 반환되거나 데이터베이스로 이동하는 모든 항목에 직접 액세스 할 수있는 것은 아닙니다.


Wordpress는 클래스의 개체를 반환합니다 StdClass. 이러한 개체는 강조 표시하는 것과 공통점이 없습니다. 예를 들어 기능이없고 상속도 없습니다. 그리고 Wordpress의 경우 모든 클래스 변수는 공용입니다.
hakre

응 그것은 사실이야. 나는이 경우 다른 사람들이 말했듯이 당신이 선호하는 것에 달려 있다고 생각합니다. 나는 wordpress에 관심이 없지만 아마도 모든 데이터베이스 호출을 캡슐화하므로 반환을위한 특수 클래스를 제공 할 수 없습니다. 하지만 내 대답은 일반적이었고 제작자가 비슷한 고려를 한 것 같습니다. 아니면 그냥 동전을 던졌습니다.
SE를 떠나는 사람이 없습니다.

그들은 stdClassca 이후 기본적으로 객체 를 반환하는 데이터베이스 도우미 클래스를 사용합니다 . 8 년. 배열을 얻으려면 선택적 매개 변수를 설정해야합니다.
hakre

3

객체를 반환하는 데는 몇 가지 이유가 있습니다.

  1. 쓰기에 $myObject->property필요한 "오버 헤드"문자는$myArray['element']

  2. 개체는 데이터와 기능을 반환 할 수 있습니다. 배열에는 데이터 만 포함될 수 있습니다.

  3. 연결 활성화 : $myobject->getData()->parseData()->toXML();

  4. 손쉬운 코딩 : IDE 자동 완성은 객체에 대한 메서드 및 속성 힌트를 제공 할 수 있습니다.

성능 측면에서 어레이는 종종 객체보다 빠릅니다. 성능 외에도 어레이를 사용하는 몇 가지 이유가 있습니다.

  1. array _ * () 함수 계열이 제공하는 기능은 경우에 따라 필요한 코딩 양을 줄일 수 있습니다.

  2. count () 및 foreach ()와 같은 작업은 배열에서 수행 할 수 있습니다. 객체는이를 제공하지 않습니다 ( Iterator 또는 Countable 을 구현하지 않는 한 ).


2

일반적으로 성능상의 이유 때문이 아닙니다. 일반적으로 객체는 배열보다 비용이 많이 듭니다.

많은 API의 경우 스토리지 메커니즘 외에 다른 기능을 제공하는 객체와 관련이있을 수 있습니다. 그렇지 않으면 선호도의 문제이며 객체 대 배열을 반환하는 데 실제로 이점이 없습니다.


PHP5에서 배열과 객체 간의 성능 차이는 미미합니다.
저스틴 ᚅᚔᚈᚄᚒᚔ

2

배열은 값의 인덱스 일뿐입니다. 객체에는 결과를 생성 할 수있는 메소드가 포함되어 있습니다. 물론 때때로 객체 값에 직접 액세스 할 수 있지만 "올바른 방법"은 객체 메서드 (해당 객체의 값에 대해 작동하는 함수)에 액세스하는 것입니다.

$obj = new MyObject;
$obj->getName();   // this calls a method (function), so it can decide what to return based on conditions or other criteria

$array['name'];   // this is just the string "name". there is no logic to it. 

때로는 객체 변수에 직접 액세스하는 경우 일반적으로 눈살을 찌푸 리지만 여전히 자주 발생합니다.

$obj->name;   // accessing the string "name" ... not really different from an array in this case.

그러나 MyObject 클래스에는 'name'이라는 변수가 없지만 대신 first_name 및 last_name 변수가 있다는 것을 고려하십시오.

$obj->getName();  // this would return first_name and last_name joined.
$obj->name;  // would fail...
$obj->first_name; 
$obj->last_name; // would be accessing the variables of that object directly.

이것은 매우 간단한 예이지만 이것이 어디로 가는지 알 수 있습니다. 클래스는 자체 포함 된 논리적 엔터티 내에서 이러한 변수에 대해 작동 할 수있는 변수 및 함수 모음을 제공합니다. 해당 엔티티의 인스턴스를 객체라고하며, 배열에는없는 논리 및 동적 결과를 도입합니다.


1

대부분의 경우 객체는 배열만큼 빠르지는 않지만 PHP에서는 눈에 띄는 차이가 없습니다. 주된 이유는 객체가 배열보다 더 강력하기 때문입니다. 객체 지향 프로그래밍은 객체를 생성하고 데이터뿐만 아니라 그 안에 기능을 저장할 수있게 해줍니다.

그래서 주된 이유는 OOP가 훌륭한 패러다임이기 때문입니다. 나는 OOP를 사용하는 것이 왜 좋은 생각인지에 대한 기사를 썼고, 개념을 설명했습니다. http://tomsbigbox.com/an-introduction-to-oop/ 에서 살펴볼 수 있습니다.

마이너 플러스로 적게 입력하여 개체에서 데이터를 가져옵니다. $ test-> data가 $ test [ 'data']보다 낫습니다.


1

저는 워드 프레스에 익숙하지 않습니다. 여기에 많은 답변이 객체의 강점은 기능 코드를 포함 할 수 있다는 것입니다. 함수 / API 호출에서 객체를 반환 할 때 유틸리티 함수를 포함해서는 안됩니다. 그냥 속성.

객체 반환의 강점은 API 뒤에있는 모든 것이 코드를 손상시키지 않고 변경 될 수 있다는 것입니다.

예 : DB 열을 나타내는 키 / 값 쌍이있는 데이터 배열을 가져옵니다. DB 열의 이름이 변경되면 코드가 손상됩니다.


1

PHP 5.3.10 (Windows)에서 다음 테스트를 실행 중입니다.

for ($i = 0; $i < 1000000; $i++) {
    $x = array();
    $x['a'] = 'a';
    $x['b'] = 'b';
}

for ($i = 0; $i < 1000000; $i++) {
    $x = new stdClass;
    $x->a = 'a';
    $x->b = 'b';
}

http://atomized.org/2009/02/really-damn-slow-a-look-at-php-objects/comment-page-1/#comment-186961 에서 복사

10 명의 동시 사용자와 10 번 (평균을 얻기 위해) 함수 호출

  • 어레이 : 100 %
  • 개체 : 214 % – 216 % (2 배 느림).

AKA, Object it is still painful slow. OOP는 물건을 깔끔하게 유지하지만 신중하게 사용해야합니다.

어떤 Wordpress가 적용됩니까?. 글쎄, 두 솔루션 모두 객체, 배열 및 객체 및 배열을 사용하고 있으며 클래스 wpdb 는 나중에 사용합니다 (그리고 Wordpress의 핵심입니다).


PHP 5.4에서 비교를 볼 수 있습니다. 객체의 성능은 탁월하며 때로는 어레이보다 더 빠릅니다.
Sanket Sahu

0

그것은 OOP의 박싱 및 언 박싱 원칙을 따릅니다. Java 및 C #과 같은 언어는 기본적으로이를 지원하지만 PHP는 지원하지 않습니다. 그러나 언어 자체가 그것을 지원하는 구조를 가지고 있지 않기 때문에 PHP에서 어느 정도는 성취 될 수 있습니다. PHP에 상자 유형을 사용하면 모든 것을 객체 지향적으로 유지하고 메소드 서명에서 유형 힌트를 허용하는 연결에 도움이 될 수 있습니다. 단점은 오버 헤드이며 이제 "instanceof"구조를 사용하여 수행 할 추가 검사가 있다는 사실입니다. 유형 시스템을 갖는 것은 또한 PDT와 같은 인텔리 센스 또는 코드 지원이있는 개발 도구를 사용할 때 장점이됩니다. 메소드에 대해 google / bing / yahoo를 수행하지 않고 객체에 존재하며 도구를 사용하여 드롭 다운을 제공 할 수 있습니다.


0

일반적으로 데이터 및 동작이기 때문에 데이터 이상의 객체에 대한 포인트는 유효 하지만 전송하려는 이러한 유형의 시나리오에 적용되는 Martin Fowler의 "Patterns of Enterprise Application Architecture"에 언급 된 패턴이 하나 이상 있습니다. 한 시스템 (API 뒤에있는 애플리케이션)과 다른 시스템 (귀하의 애플리케이션)의 데이터.

그것 데이터 전송 개체 - 메소드 호출의 수를 줄이기 위해 프로세스간에 데이터를 전달하는 객체입니다.

따라서 질문이 API가 DTO 또는 어레이를 반환해야하는지 여부 인 경우 성능 비용이 무시할 수있는 수준이면 유지 관리가 더 쉬운 옵션을 선택해야하며 DTO 옵션이라고 생각합니다. 시스템을 개발하는 팀의 기술과 문화와 각 옵션에 대한 언어 또는 IDE 지원을 고려해야합니다.

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