[java] Java 인터페이스와 Objective-C 프로토콜의 차이점은 무엇입니까?

저는 Java를 알고 있으며 이제 Objective-C를 배우고 있습니다. Java 인터페이스와 Objective-C 프로토콜의 차이점은 정확히 무엇입니까?



답변

먼저, Java 제작자 중 한 사람이 주제에 대한 약간의 역사적 관점을 살펴 보겠습니다. 다음으로, Wikipedia에는 Objective-C 프로토콜에 대해 적당히 유용한 섹션이 있습니다 . 특히, Objective-C는 공식 프로토콜 ( @protocolJava 인터페이스에 해당 하는 키워드 로 명시 적으로 선언 됨 )과 비공식 프로토콜 (반영을 통해 발견 할 수있는 클래스에 의해 구현 된 하나 이상의 메소드 )을 모두 지원한다는 점을 이해 하십시오 .

공식 프로토콜 ( “인터페이스 구현”에 대한 Objective-C 용어)을 채택하면 컴파일러는 Java에서 예상하는 것처럼 구현되지 않은 메서드에 대한 경고를 내 보냅니다. Java ( skaffman이 언급했듯이) 와 달리 Objective-C 클래스가 공식 프로토콜에 포함 된 메소드를 구현하면 인터페이스가 명시 적으로 채택하지 않더라도 해당 프로토콜을 “준수”한다고합니다.다음 과 같이 코드에서 프로토콜 적합성을 테스트 할 수 있습니다 ( -conformsToProtocol : 사용 ).

if ([myObject conformsToProtocol:@protocol(MyProtocol)]) {
    ...
}

참고 : Apple의 설명서 에는 다음과 같은 내용이 있습니다.

“이 방법은 위에 설명 된대로 헤더 파일의 공식 선언을 기준으로 만 적합성을 결정합니다. 프로토콜에 선언 된 메서드가 실제로 구현되었는지 여부를 확인하지 않습니다. 이것이 프로그래머의 책임입니다.”

Objective-C 2.0 (OS X 10.5 “Leopard”및 iOS)부터는 이제 공식 프로토콜이 선택적 메소드를 정의 할 수 있으며 클래스는 모든 필수 메소드를 구현하는 한 프로토콜을 준수합니다. @required(기본값) 및 @optional키워드를 사용하여 뒤에 오는 메서드 선언이 프로토콜을 준수하도록 구현 되어야 하는지 또는 구현 수 있는지 여부를 전환 할 수 있습니다. ( 옵션 프로토콜 방법 을 설명하는 Apple의 Objective-C 2.0 프로그래밍 언어 가이드 섹션을 참조하십시오 .)

선택적 프로토콜 메서드는 특히 델리게이트리스너 를 구현하는 개발자에게 많은 유연성을 제공 합니다. MouseInputAdapter 와 같은 것을 확장하거나 (Java도 단일 상속이기 때문에 성 가실 수 있음) 많은 무의미하고 빈 메서드를 구현하는 대신 프로토콜을 채택하고 관심있는 선택적 메서드 만 구현할 수 있습니다. 이 패턴을 사용하면 호출자는 다음과 같이 메서드를 호출하기 전에 ( -respondsToSelector 사용 ) 메서드가 구현되었는지 확인합니다 .

if ([myObject respondsToSelector:@selector(fillArray:withObject:)]) {
    [myObject fillArray:anArray withObject:foo];
    ...
}

리플렉션의 오버 헤드가 문제가되는 경우 언제든지 부울 결과를 재사용하여 캐시 할 수 있지만 조기에 최적화하려는 충동은 억제합니다. 🙂


답변

거의 동일합니다. 그러나 나를 붙잡은 한 가지는 객관적인 C 프로토콜이 NSObject를 구현한다고 명시 적으로 선언하지 않는 한 해당 프로토콜에 대한 참조는 NSObject가 선언하는 메서드에 액세스 할 수 없다는 것입니다 (어쨌든 컴파일러 경고없이). 자바를 사용하면 인터페이스에 대한 참조를 가질 수 있으며 여전히 toString () 등을 호출 할 수 있습니다.

예 :

목표 C :

@protocol MyProtocol
// Protocol definition
@end

id <MyProtocol> myProtocol;

 [myProtocol retain] // Compiler warning

자바:

public interface MyInterface {
// interface definition
}

MyInterface myInterface;

myInterface.toString();  // Works fine.

목표 C (고정) :

@protocol MyProtocol <NSObject>
// Protocol definition
@end

id <MyProtocol> myProtocol;

[myProtocol retain] // No Warning


답변