프로토타입 기반 프로그래밍
Prototype-based programming| 프로그래밍 패러다임 |
|---|
프로토타입 기반 프로그래밍은 프로토타입으로 사용되는 기존 객체를 재사용하는 프로세스를 통해 동작 재사용(상속이라고 함)이 수행되는 객체 지향 프로그래밍 스타일입니다.이 모델은 프로토타입, 프로토타입 지향, 클래스리스 또는 인스턴스 기반 프로그래밍이라고도 합니다.
프로토타입 기반 프로그래밍은 프로세스 일반화된 개체를 사용하며, 이 개체는 복제 및 확장할 수 있습니다.과일을 예로 들면, "과일" 물체는 일반적으로 과일의 특성과 기능을 나타낼 것입니다."바나나" 개체는 "과일" 개체에서 복제되고 바나나에 대한 일반적인 특성이 부가됩니다.각각의 "바나나" 개체는 일반적인 "바나나" 개체에서 복제됩니다."과일" 클래스가 "바나나" 클래스로 확장되는 클래스 기반 패러다임과 비교해 보십시오.
최초의 프로토타입 지향 프로그래밍 언어는 Self로, 1980년대 중반 David Ungar와 Randall Smith에 의해 객체 지향 언어 디자인의 주제를 연구하기 위해 개발되었습니다.1990년대 후반부터 계급 없는 패러다임이 점점 인기를 끌고 있다.현재 프로토타입 지향 언어로는 JavaScript(및 JScript 및 Flash의 ActionScript 1.0과 같은 기타 ECMAScript 구현), Lua, Cecil, NewtonScript, Io, Ioke, MOU, REBOL 및 AHK가 있습니다.
설계 및 구현
JavaScript의 프로토타입 상속은 Douglas Crockford가 다음과 같이 설명합니다.
프로토타입 오브젝트를 만들고 새로운 인스턴스를 만듭니다.오브젝트는 JavaScript에서 변경할 수 있으므로 새로운 인스턴스를 증강하여 새로운 필드와 메서드를 제공할 수 있습니다.그런 다음 더 새로운 객체의 프로토타입 역할을 할 수 있습니다.비슷한 오브젝트를 많이 만들기 위해 클래스가 필요하지 않습니다. 오브젝트는 오브젝트로부터 상속됩니다.이것보다 [1]더 객체 지향적인 것은 무엇일까요?
프로토타입 기반 프로그래밍의 지지자들은 이것이 프로그래머가 일련의 예들의 행동에 초점을 맞추도록 장려하고 나중에 [2]이러한 오브젝트를 클래스와 유사한 방식으로 사용되는 원형 오브젝트로 분류하는 것에 대해서만 걱정하게 한다고 주장한다.많은 프로토타입 기반 시스템은 런타임 중에 프로토타입의 변경을 장려하는 반면, 클래스 기반 객체 지향 시스템(동적 객체 지향 시스템, Common Lisp, Dylan, Objective-C, Perl, Python, Ruby 또는 Smalltalk 등)은 프로그램 실행 중에 클래스를 변경할 수 있는 경우가 거의 없습니다.
거의 모든 프로토타입 기반 시스템은 해석되고 동적으로 입력된 언어를 기반으로 합니다.그러나 정적으로 입력된 언어를 기반으로 하는 시스템은 기술적으로 실현 가능합니다.프로토타입 기반 프로그래밍에서[3] 논의된 오메가 언어는 비록 오메가 웹사이트가 독점적으로 정적인 것이 아니라 "컴파일러가 이것이 가능한 곳에서 정적인 바인딩을 사용하는 것을 선택할 수 있고 프로그램의 효율성을 향상시킬 수 있다"고 하지만, 그러한 시스템의 한 예이다.
오브젝트 구성
프로토타입 기반 언어에는 명시적 클래스가 없습니다.개체는 프로토타입 속성을 통해 다른 개체로부터 직접 상속됩니다.프로토타입 속성은prototypeSelf 및 JavaScript 또는protoIo. 새로운 오브젝트를 작성하는 방법에는 두 가지가 있습니다.예를 들어 nihilo("무에서") 오브젝트 작성과 기존 오브젝트 복제를 통한 방법이 있습니다.전자는 다음과 같은 특별한 구문을 통해 런타임에 개체를 정의할 수 있는 선언인 객체 리터럴 형식을 통해 지원됩니다.{...}변수로 직접 전달됩니다.대부분의 시스템이 다양한 복제를 지원하지만 nihilo 객체 생성은 그다지 [4]두드러지지 않습니다.
클래스 베이스 언어에서 새로운 인스턴스는 클래스의 생성자 함수를 통해 구성됩니다.이 함수는 객체의 멤버(속성 및 메서드)를 위해 메모리 블록을 예약하고 해당 블록에 대한 참조를 반환하는 특수 함수입니다.선택적 생성자 인수 집합은 함수에 전달될 수 있으며 일반적으로 속성으로 유지됩니다.결과 인스턴스는 클래스에 정의된 모든 메서드와 속성을 상속합니다.이 메서드는 유사한 유형의 개체를 구성할 수 있는 템플릿의 일종입니다.
nihilo 객체 생성을 지원하는 시스템에서는 기존 프로토타입에서 복제하지 않고도 새로운 객체를 처음부터 생성할 수 있습니다.이러한 시스템은 기존 개체를 참조하지 않고 새 개체의 속성 및 동작을 지정하기 위한 특별한 구문을 제공합니다.많은 프로토타입 언어에는 루트 오브젝트(종종 오브젝트)가 존재하며 런타임에 작성된 다른 모든 오브젝트의 기본 프로토타입으로 설정되며 다음과 같이 일반적으로 필요한 메서드를 전송합니다.toString()개체의 설명을 문자열로 반환하는 함수입니다.nihilo 오브젝트 작성의 유용한 측면 중 하나는 새로운 오브젝트의 슬롯(속성 및 메서드) 이름이 최상위 오브젝트 오브젝트와 네임스페이스 경합을 갖지 않도록 하는 것입니다.(JavaScript 언어에서는 null 프로토타입을 사용하여 이를 수행할 수 있습니다.Object.create(null).)
클로닝은 기존 오브젝트(프로토타입)의 동작을 복사하여 새로운 오브젝트를 구성하는 프로세스를 말합니다.그러면 새로운 물체는 원본의 모든 특성을 갖습니다.이 시점부터 새 개체를 수정할 수 있습니다.일부 시스템에서는 결과 자식 개체가 프로토타입에 대한 명시적 링크(위임 또는 유사성을 통해)를 유지하며, 프로토타입의 변경으로 인해 클론에서 해당 변경 사항이 분명하게 나타납니다.Fourth와 유사한 프로그래밍 언어 Kevo와 같은 다른 시스템은 이러한 방식으로 프로토타입에서 변경을 전파하지 않고 대신 복제된 개체의 변경이 하위 [2]개체 간에 자동으로 전파되지 않는 보다 연결적인 모델을 따릅니다.
// 실제 시제품 상속 스타일의 예 // JavaScript에서. // 리터럴을 사용한 객체 생성 // 개체 표기법 {}. 컨스턴트 후우 = { 이름.: "푸", 하나.: 1, 두명: 2 }; // 다른 개체입니다. 컨스턴트 막대기 = { 두명: '둘', 세개: 3 }; // 객체.setProtypeOf()는 ECMAScript 2015에서 도입된 메서드입니다. //간단하게 하기 위해, 우리가 가장하자. // 다음 행은 다음 행에 관계없이 동작합니다. // 사용된 엔진: 물건.set Protype Of(막대기, 후우); // foo는 이제 막대의 원형입니다. // 바에서 foo의 속성에 액세스하려고 하면 // 지금부터, 우리는 성공할 것이다. 막대기.하나.; // 1로 해결됩니다. // 하위 개체의 속성에도 액세스할 수 있습니다. 막대기.세개; // 3으로 해결됩니다. // 자체 속성 섀도우 프로토타입 속성 막대기.두명; // "2"로 해결 막대기.이름.; // 영향을 받지 않고 "foo"로 해결 후우.이름.; // "foo"로 해결 다른 예로는 다음과 같습니다.
컨스턴트 후우 = { 하나.: 1, 두명: 2 }; // bar . [ foo ]= foo 컨스턴트 막대기 = 물건.만들다(후우); 막대기.세개 = 3; 막대기.하나.; // 1 막대기.두명; // 2 막대기.세개; // 3 위임
위임을 사용하는 프로토타입 기반 언어에서 언어 런타임은 일치하는 항목이 발견될 때까지 일련의 위임 포인터를 따르는 것만으로 올바른 메서드를 디스패치하거나 올바른 데이터 조각을 찾을 수 있습니다.개체 간에 이 동작 공유를 확립하기 위해 필요한 것은 위임 포인터뿐입니다.클래스 기반 객체 지향 언어에서의 클래스 및 인스턴스 간의 관계와는 달리, 프로토타입과 그 오프쇼트 간의 관계는 하위 객체가 이 링크를 넘어 프로토타입과 메모리 또는 구조적 유사성을 가질 필요가 없습니다.따라서 하위 개체는 클래스 기반 시스템에서와 같이 연관된 프로토타입의 구조를 재정렬하지 않고도 시간이 지남에 따라 계속 수정 및 수정할 수 있습니다.또한 데이터뿐만 아니라 메서드를 추가하거나 변경할 수 있다는 점도 중요합니다.이러한 이유로 일부 프로토타입 기반 언어에서는 데이터와 방법을 모두 "슬롯" 또는 "구성원"[citation needed]이라고 부릅니다.
연결
Kevo 프로그래밍 언어로 구현된 접근 방식인 연결 프로토타이핑에서는 개체가 복제되는 원래 프로토타입에 대한 가시적인 포인터나 링크가 없습니다.프로토타입(상위) 오브젝트는 링크되지 않고 복사되며 위임이 없습니다.따라서 프로토타입의 변경 내용은 복제된 [5]개체에 반영되지 않습니다.
이 배치의 주요 개념적 차이는 프로토타입 객체에 대한 변경 내용이 자동으로 복제로 전파되지 않는다는 것입니다.이것은 장점과 단점으로 볼 수 있습니다.(단, Kevo는 위임 모델에서 일반적인 분류학적 기원이 아닌 유사성(일명 패밀리 유사성 또는 클론 패밀리[5] 메커니즘)에 기초한 개체 집합 간의 변경 내용을 게시하기 위한 추가 프리미티브를 제공합니다).또한 위임 기반 프로토타이핑은 하위 객체의 변경이 상위 객체의 향후 운영에 영향을 미칠 수 있다는 점에서 추가적인 단점이 있다고 주장하기도 한다.단, 이 문제는 위임 기반 모델에는 고유하지 않으며 JavaScript와 같은 위임 기반 언어에는 존재하지 않습니다.이를 통해 자식 개체에 대한 변경은 항상 자식 개체 자체에만 기록되고 부모 개체에는 기록되지 않습니다(즉, 자식 값이 부모 값을 변경하는 것이 아니라 부모 값을 음영으로 표시됨).
단순 구현에서 연결 프로토타이핑은 위임 기반 프로토타이핑보다 멤버 조회가 빠릅니다(부모 개체 체인을 따를 필요가 없기 때문에). 그러나 반대로 상위 개체를 가리키는 단일 슬롯이 있는 것보다 모든 슬롯이 복사되기 때문에 더 많은 메모리를 사용합니다.다만, 보다 고도의 실장에서는, 속도와 메모리의 밸런스가 필요하지만, 이 문제를 회피할 수 있습니다.예를 들어, 연결 프로토타이핑을 사용하는 시스템에서는 쓰기 시 복사 구현을 사용하여 백그라운드 데이터 공유를 허용할 수 있습니다. 이러한 접근 방식은 실제로 Kevo가 [6]따르고 있습니다.반대로 위임 기반 프로토타이핑을 사용하는 시스템에서는 캐싱을 사용하여 데이터 검색 속도를 높일 수 있습니다.
비판
프로토타입 기반 시스템을 비판하는 클래스 기반 객체 모델의 지지자들은 프로그래밍 언어를 위한 정적 유형 시스템의 지지자들이 동적 유형 시스템에 대해 가지고 있는 우려와 유사한 우려를 가지고 있다(데이터 유형 참조).일반적으로 이러한 우려에는 정확성, 안전성, 예측 가능성, 효율성 및 프로그래머의 생소함이 포함됩니다.
처음 세 가지 점에서 클래스는 종종 유형(대부분 정적 유형 객체 지향 언어에서 해당 역할을 수행함)과 유사한 것으로 간주되며, 해당 인스턴스와 해당 인스턴스의 사용자에게 주어진 방식으로 동작한다는 계약상 보증을 제공하도록 제안됩니다.
효율성에 관해서는 클래스를 선언하면 효율적인 메서드와 인스턴스 변수 검색을 개발할 수 있는 많은 컴파일러 최적화가 단순해집니다.Self language의 경우 클래스 기반 시스템과 비교하여 프로토타입 기반 시스템의 성능을 개선하기 위한 기술 개발, 컴파일 및 해석에 많은 시간이 소요되었습니다.
프로토타입 기반 언어에 대한 일반적인 비판은 JavaScript의 인기와 시장 침투에도 불구하고 소프트웨어 개발자 커뮤니티가 익숙하지 않다는 것입니다.이러한 프로토타입 기반 시스템의 지식 수준은 JavaScript 프레임워크의 확산과 웹이 [7][citation needed]성숙함에 따라 JavaScript의 복잡한 사용과 함께 증가하고 있는 것으로 보입니다.ECMAScript 6은 클래스를 JavaScript의 기존 프로토타입 기반 상속보다 구문적인 설탕으로 도입하여 개체를 생성하고 [8]상속을 처리하는 대체 방법을 제공합니다.
프로토타입 기반 프로그래밍을 지원하는 언어
- 배우 기반 동시 언어(ABCL): ABCL/1, ABCL/R, ABCL/R2, ABCL/c+
- 아고라
- 자동 단축키
- 크레이그 체임버스의 세실과 디젤
- 콜드C
- 콜라
- 일반적인 리스프
- 청록색
- ECMAScript
- 이오
- 이오케
- Jsonnet
- 로그토크
- LPC
- 루아
- M2000
- 메이플
- 무
- 네코
- 뉴턴스크립트
- 님
- 닉스
- 오브젝트 리스프
- 오블리크
- 오메가
- 오픈라즐로
- Perl, 클래스:시제품 모듈
- Python with prototype.py.
- R, 프로토타입 패키지 포함
- 리볼
- 빨간색(프로그래밍 언어)
- 루비(프로그래밍 언어)
- 자신
- 셉
- 슬레이트(프로그래밍 언어)
- 스마트 개구리
- 찰칵!
- 이토이스
- TADS
- 슬롯 확장 Tcl
- 우마진[9]
「 」를 참조해 주세요.
- 클래스 베이스 프로그래밍(콘트라스트)
- 차등 상속
- 프로그래밍 패러다임
레퍼런스
- ^ Crockford, Douglas. "Prototypal Inheritance in JavaScript". Retrieved 22 June 2021.
- ^ a b Taivalsaari, Antero (1996). "Section 1.1". Classes vs. Prototypes: Some Philosophical and Historical Observations. pp. 44–50. CiteSeerX 10.1.1.56.4713.
- ^ Blaschek, Günther. "Section 2.8". Omega: Statically Typed Prototypes. p. 177.
- ^ Dony, Chistophe; Malenfan, Jacques; Bardou, Daniel. "Section 1.2" (PDF). Classifying Prototype-based Programming Languages. p. 17.
- ^ a b Antero Taivalsaar (2009). "Simplifying JavaScript with Concatenation-Based Prototype Inheritance" (PDF). Tampere University of Technology. Archived from the original on 2009. Retrieved 2015-03-11.
Kevo implemented a pure concatenation-based object model in which new objects were created by copying and the namespaces of all the objects were always fully self-contained. … Furthermore, Kevo had an internal clone family mechanism that made it possible to track the “genealogy” of changes among groups of objects, so that changes to individual objects could be propagated to other objects when necessary.
- ^ Taivalsaari, Antero (1992). "Kevo, a prototype-based object-oriented programming language based on concatenation and module operations". Technical Report Report LACIR 92-02. University of Victoria.
- ^ "Prototypal Object-Oriented Programming using JavaScript". A List Apart. 2016-04-26. Retrieved 2018-10-21.
- ^ "Classes". JavaScript reference. Mozilla Developer Network. Retrieved 9 February 2016.
- ^ 독자적인 스크립트 언어http://www.davidbrebner.com/?p=4에는 몇 가지 기본적인 사용 예가 있습니다.
추가 정보
- Abadi, Martin; Luca Cardelli (1996). A Theory of Objects. Springer-Verlag. ISBN 978-1-4612-6445-3.
- 클래스 워: 클래스 vs. Brian Foote의 시제품.
- Noble, James; Taivalsaari, Antero; Moore, Ivan, eds. (1999). Prototype-Based Programming: Concepts, Languages and Applications. Springer-Verlag. ISBN 981-4021-25-3.
- Henry Lieberman, 1986년, 프로토타입 객체를 사용하여 객체 지향 시스템에서 공유 동작을 구현합니다.