R에서 "S3 방법"은 무엇을 의미합니까?


124

저는 R을 처음 접했기 때문에 S3 메서드와 객체가 무엇인지 모릅니다. S3 및 S4 객체 시스템이 있으며 일부는 가능하면 S4보다 S3를 사용하도록 권장합니다 ( http://google-styleguide.googlecode.com/svn/trunk/google-r-style 에서 Google의 R 스타일 가이드 참조). html ) *. 그러나 S3 메서드 / 객체의 정확한 정의를 모릅니다.

업데이트 : 2019 년부터 Google의 R 스타일 가이드 하이퍼 링크가 여기 있습니다 .

답변:


85

관련 정보의 대부분은 보면 볼 수 있습니다 ?S3또는 ?UseMethod, 그러나 요컨대 :

S3는 메소드 디스패치 방식을 나타냅니다. 한동안 R을 사용했다면 다양한 종류의 객체에 대한 print, predictsummary메서드 가 있음을 알 수 있습니다.

S3에서는 다음과 같이 작동합니다.

  • 관심있는 객체의 클래스 설정 (예 : 메서드 호출의 반환 값에 glmclass가 있음 glm)
  • 일반 이름 (예 print:), 점, 클래스 이름 (예 : print.glm )
  • 이 작업을 수행하려면이 일반 이름 ( print)에 대해 약간의 준비 작업을 수행해야 하지만 단순히 기존 메서드 이름을 따르려는 경우에는이 작업이 필요하지 않습니다. ).

보는 사람, 특히 새로 만든 펑키 모델 피팅 패키지 사용자의 눈에는 .NET Framework predict(myfit, type="class")보다 타이핑 할 수있는 것이 훨씬 더 편리합니다 predict.mykindoffit(myfit, type="class").

더 많은 내용이 있지만 시작해야합니다. 객체의 속성 (클래스)을 기반으로 메서드를 디스패치하는 방법에는 몇 가지 단점이 있지만 (그리고 C 순수 주의자들은 아마도 밤에 끔찍하게 깨어있을 것입니다), 많은 상황에서 제대로 작동합니다. 현재 버전의 R에서는 새로운 방식 (S4 및 참조 클래스)이 구현되었지만 대부분의 사람들은 여전히 ​​S3를 사용합니다.


54

S3를 시작하려면 median함수 코드를 확인하세요 . median명령 프롬프트에 입력 하면 본문에 한 줄이 있음을 알 수 있습니다.

UseMethod("median")

즉, S3 방법입니다. 즉, medianS3 클래스마다 다른 기능을 가질 수 있습니다 . 가능한 모든 중앙값 방법을 나열하려면 다음을 입력하십시오.

methods(median) #actually not that interesting.  

이 경우, 모든 것에 대해 호출되는 기본 메서드는 하나뿐입니다. 입력하여 코드를 볼 수 있습니다.

median.default

훨씬 더 흥미로운 예는 print다양한 방법 이있는 함수입니다.

methods(print)  #very exciting

일부 메서드에는 *이름 옆에 s 가 있습니다 . 즉, 일부 패키지의 네임 스페이스 내에 숨겨져 있습니다. find어떤 패키지에 들어 있는지 확인하는 데 사용 합니다. 예를 들어

find("acf")  #it's in the stats package
stats:::print.acf

39

에서 http://adv-r.had.co.nz/OO-essentials.html :

R의 세 가지 OO 시스템은 클래스와 메서드가 정의되는 방식이 다릅니다.

  • S3는 일반 함수 OO라고하는 OO 프로그래밍 스타일을 구현합니다. 이것은 메시지 전달 OO를 구현하는 Java, C ++ 및 C #과 같은 대부분의 프로그래밍 언어와 다릅니다. 메시지 전달을 사용하면 메시지 (메서드)가 객체로 전송되고 객체가 호출 할 함수를 결정합니다. 일반적으로이 객체는 메서드 호출에서 특별한 모양을 가지며 일반적으로 메서드 / 메시지 이름 앞에 나타납니다. 예 : canvas.drawRect ( "blue"). S3는 다릅니다. 계산은 여전히 ​​메서드를 통해 수행되지만 일반 함수라고하는 특수한 유형의 함수는 호출 할 메서드를 결정합니다 (예 : drawRect (canvas, "blue")). S3는 매우 캐주얼 한 시스템입니다. 클래스에 대한 공식적인 정의가 없습니다.

  • S4는 S3와 유사하게 작동하지만 더 형식적입니다. S3에는 두 가지 주요 차이점이 있습니다. S4에는 각 클래스의 표현 및 상속을 설명하는 형식적인 클래스 정의가 있으며 제네릭 및 메서드를 정의하기위한 특수 도우미 함수가 있습니다. S4에는 또한 여러 개의 디스패치가 있습니다. 즉, 일반 함수는 하나가 아닌 여러 인수의 클래스를 기반으로 메서드를 선택할 수 있습니다.

  • 간단히 RC라고하는 참조 클래스는 S3 및 S4와 상당히 다릅니다. RC는 메시지 전달 OO를 구현하므로 메서드는 함수가 아닌 클래스에 속합니다. $는 객체와 메서드를 분리하는 데 사용되므로 메서드 호출은 canvas $ drawRect ( "blue")처럼 보입니다. RC 객체도 변경 가능합니다. R의 일반적인 수정시 복사 의미를 사용하지 않지만 제자리에서 수정됩니다. 이로 인해 추론하기가 더 어려워 지지만 S3 또는 S4로 해결하기 어려운 문제를 해결할 수 있습니다.

OO가 아닌 다른 시스템도 있지만 여기서 언급하는 것이 중요합니다.

  • 기본 유형, 다른 OO 시스템의 기초가되는 내부 C 레벨 유형. 기본 유형은 대부분 C 코드를 사용하여 조작되지만 다른 OO 시스템에 대한 빌딩 블록을 제공하기 때문에 알아야 할 중요합니다.

11

나는 이름이 어디에서 왔는지 주로 궁금해하는 질문에 왔습니다. 이 위키피디아 기사 에서 이름이 R의 기반이되는 S 프로그래밍 언어 버전을 참조 하는 것으로 나타났습니다 . 다른 답변에 설명 된 메서드 디스패치 체계는 S에서 왔으며 버전에 따라 적절하게 레이블이 지정됩니다.


10

시험

methods(residuals)

무엇보다도 "residuals.lm"및 "residuals.glm"이 나열됩니다. 즉, 선형 모델, m 및 유형을 피팅했을 때residuals(m), Residuals.lm이 호출됩니다. 일반화 선형 모델을 피팅하면 잔차 .glm이 호출됩니다. 거꾸로 뒤집힌 C ++ 개체 모델의 일종입니다. C ++에서는 파생 클래스에 의해 재정의되는 가상 함수가있는 기본 클래스를 정의합니다. R에서 가상 (일반) 함수를 정의한 다음이 함수를 재정의 할 클래스를 결정합니다 (즉, 메서드 정의). 이 작업을 수행하는 클래스는 하나의 공통 수퍼 클래스에서 파생 될 필요가 없습니다. 일반적으로 S4보다 S3를 선호하는 데 동의하지 않습니다. S4는 형식주의 (= 더 많은 타이핑)를 가지고 있으며 일부 응용 프로그램에는 너무 많을 수 있습니다. 그러나 S4 클래스는 C ++의 클래스 또는 구조체처럼 정의 될 수 있습니다. 특정 클래스의 객체가 문자열과 두 개의 숫자로 구성되도록 지정할 수 있습니다. 예를 들면 다음과 같습니다.

setClass("myClass", representation(label = "character", x = "numeric", y = "numeric"))

해당 클래스의 개체와 함께 호출되는 메서드는 해당 멤버가있는 개체에 의존 할 수 있습니다. 이는 요소의 목록 일 뿐인 S3 클래스와는 매우 다릅니다.

S3과 S4, 당신은으로 멤버 함수를 호출 fun(object, args)하여하지 object$fun(args). 후자와 같은 것을 찾고 있다면 proto 패키지를 살펴보십시오.


나는 객체에 속하는 멤버 함수와 메소드의 개념이 R에서 그다지 의미가 없다고 확신합니다. 메소드는 객체에 속하지 않고 (함수도 객체이기도합니다) 함수에 속합니다.
petermeissner

3

다음은 Hadley Wickham (RStudio의 수석 과학자)의 "Advanced R, 2nd edition" (CRC Press, 2019)에 따른 수많은 R 객체 시스템 의 업데이트 된 빠른 요약입니다. 여기 에는 Object 에 대한 장을 기반으로 한 웹 표현이 있습니다 . -지향적 프로그래밍 .

고급 R 책 표지

2015 년 초판은 여기에 웹 표현이 있고 여기 에 OO에 대한 해당 장이 있습니다 .

OO 시스템에 대한 접근

Hadley는 OO 프로그래밍에 대한 두 가지 다른 접근 방식을 구별하기 위해 다음을 정의합니다.

기능적 OOP : 메소드 (호출 가능한 코드 조각)는 일반 함수 에 속합니다 (Java / C # 일반 메소드 와 혼동하지 마십시오 ). 메소드를 전역 조회 테이블에있는 것으로 생각하십시오. 실행할 메서드는 함수 이름과 해당 함수에 전달 된 하나 이상의 인수 유형 (또는 객체 클래스)을 기반으로 런타임 시스템에서 찾습니다 (이를 "메서드 디스패치"라고 함). 구문 측면에서 메서드 호출은 일반 함수 호출처럼 보일 수 있습니다 myfunc(object, arg1, arg2).. 이 호출은 런타임이 쌍 ( "myfunc", typeof (object)) 또는 가능하면 ( "myfunc", typeof (object), typeof (arg1), typeof (arg2)) 와 연관된 메소드를 찾도록 유도합니다.언어가 지원한다면. R의 S3에서 일반 함수의 전체 이름은 (함수 이름, 클래스)쌍. 예 : mean.Date날짜의 평균을 계산하는 방법입니다. methods("mean")함수 이름으로 일반 메소드를 나열 해보십시오 mean. 기능적 OOP 접근법은 예를 들어 OO의 개척자 Smalltalk , Common Lisp Object SystemJulia에서 찾을 수 있습니다. Hadley는 "R과 비교할 때 Julia의 구현은 완전히 개발되었으며 매우 성능이 뛰어납니다."라고 말합니다.

캡슐화 된 OOP : 메서드는 개체 또는 클래스에 속하며 메서드 호출은 일반적으로 object.method(arg1, arg2). 객체가 데이터 (필드)와 동작 (메소드)을 모두 캡슐화 하기 때문에 이를 캡슐화 라고합니다 . 메서드를 객체 또는 객체의 클래스 설명에 첨부 된 조회 테이블에있는 것으로 생각하십시오. 런타임은 메서드 이름과 하나 이상의 인수 유형을 기반으로 메서드를 찾습니다. 이것은 C ++, Java, C #과 같은 "인기있는"OO 언어에서 발견되는 접근 방식입니다.

두 경우 모두 상속이 지원되는 경우 (아마도 가능) 런타임은 호출 조회 키와 일치하는 항목을 찾을 때까지 클래스 계층 구조를 위쪽으로 탐색 할 수 있습니다.

R 객체가 속한 시스템을 찾는 방법

library(sloop) # formerly, "pryr"
otype(mtcars)
#> [1] "S3"

R 개체 시스템

S3

  • 기능적 OOP 접근 방식.
  • Hadley에 따르면 가장 중요한 시스템입니다.
  • 가장 간단하고 일반적입니다. R이 사용한 최초의 OO 시스템.
  • base R 전체에 사용되는 base R이 함께 제공됩니다.
  • 강제 보장이 아닌 규칙에 의존합니다.
  • Chambers, John M 및 Trevor J Hastie를 참조하십시오 . 1992. "S의 통계 모델" Wadsworth & Brooks / Cole 고급 도서 및 소프트웨어.
  • "Advanced R, 2nd edition"에 대한 자세한 내용은 여기 .

S4

  • 기능적 OOP 접근 방식.
  • Hadley에 따르면 세 번째로 중요한 시스템입니다.
  • 따라서 S3를 다시 작성하면 S3와 비슷하지만 더 형식적이고 더 엄격합니다. 프로그램 설계에 대해 신중하게 생각해야합니다. 대규모 시스템 구축에 적합합니다 (예 : Bioconductor 프로젝트).
  • 기본 "방법"패키지에서 구현됩니다.
  • 참조 : Chambers, John M. 1998. "Programming with Data : A Guide to the S Language." 봄 병아리.
  • "Advanced R, 2nd edition"에 대한 자세한 내용은 여기 .

RC 일명 "참조 클래스"

  • 캡슐화 된 OOP 접근 방식.
  • 베이스 R과 함께 제공됩니다.
  • S4 기반.
  • RC 객체는 "변경 가능"한 특수한 유형의 S4 객체입니다. 즉, R의 일반적인 copy-on-modify 의미 체계를 사용하는 대신 제자리에서 수정할 수 있습니다. 변경 가능한 상태는 추론하기 어렵고 보기 흉한 버그의 원인이지만 특정 애플리케이션에서 더 효율적인 코드로 이어질 수 있습니다.

R6

  • 캡슐화 된 OOP 접근 방식.
  • Hadley에 따르면 두 번째로 중요한 시스템입니다.
  • R6 패키지 에서 찾을 수 있습니다 (로 설치 library(R6)).
  • RC와 유사하지만 더 가볍고 더 빠릅니다. S4 또는 메소드 패키지 에 의존하지 않습니다 . R 환경 위에 구축되었습니다. 또한 :
    • 공개 및 비공개 방법
    • 활성 바인딩 (액세스 할 때 실제로 메서드를 호출하는 필드)
    • 패키지간에 작동하는 클래스 상속
    • 모두 클래스 메소드 (클래스에 속하는 통해 인스턴스를 액세스 할 수있는 코드 self, private, super)와 멤버 함수 (필드에 할당 된 기능, 그러나 방법되지 않은 단 기능)
  • R의 "수정시 복사"의미 체계를 벗어나는 표준화 된 방법을 제공합니다.
  • 패키지 사이트 : "R6 : R을위한 캡슐화 된 객체 지향 프로그래밍"을 참조하십시오 .
  • "Advanced R, 2nd edition"에 대한 자세한 내용은 여기 .

기타

같은 사람이 있습니다 R.oo (RC 유사), 킬로그램 (프로토 타입 기반, 자바 스크립트를 생각한다) 및 Mutatr는 . 그러나 "Advanced R"은 다음과 같이 말합니다.

널리 사용되는 R6 외에도 이러한 시스템은 주로 이론적 관심사입니다. 그들은 강점을 가지고 있지만 R 사용자는 거의 알고 이해하지 않으므로 다른 사람들이 코드를 읽고 기여하기가 어렵습니다.

"Advanced R, 2nd edition"의 트레이드 오프 에 대한 장도 읽어보십시오 .

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