수색…


비고

인터페이스는 명시 적 구현 정보를 제공하지 않고 필요한 정보와 메소드 및 클래스의 예상 출력을 설명하는 데 사용됩니다.

클래스는 인터페이스를 구현할 수 있고 인터페이스는 서로 상속 할 수 있습니다. 클래스가 인터페이스를 구현 하는 경우 이는 인터페이스에 의해 노출 된 모든 함수와 프로 시저가 클래스에 있음을 의미합니다.

델파이의 인터페이스의 특별한 측면은 인터페이스의 인스턴스가 참조 카운팅에 기반한 평생 관리를한다는 것입니다. 클래스 인스턴스의 수명은 수동으로 관리해야합니다.

이러한 모든 측면을 고려하여 인터페이스를 사용하여 서로 다른 목표를 달성 할 수 있습니다.

  • 작업 (예 : 파일 저장, 데이터베이스 저장 또는 전자 메일 전송, 모두 "SaveData"인터페이스)에 대한 여러 가지 구현 제공
  • 종속성 감소, 디커플링 개선 및 코드 유지 관리 및 테스트 가능
  • 평생 관리에 문제가 발생하지 않고 여러 단위로 인스턴스와 작업합니다 (여기에도 함정이 존재하지만 조심하십시오!).

인터페이스 정의 및 구현

인터페이스는 클래스처럼 선언되지만 액세스 수정 자 ( public , private , ...)는 없습니다. 또한 정의가 허용되지 않으므로 변수와 상수를 사용할 수 없습니다.

인터페이스에는 Ctrl + Shift + G를 눌러 생성 할 수있는 고유 식별자 가 항상 있어야합니다.

IRepository = interface
    ['{AFCFCE96-2EC2-4AE4-8E23-D4C4FF6BBD01}']
    function  SaveKeyValuePair(aKey: Integer; aValue: string): Boolean;
end;

인터페이스를 구현하려면 인터페이스 이름을 기본 클래스 뒤에 추가해야합니다. 또한 클래스는 TInterfacedObject 의 자손이어야합니다 ( 수명 관리에 중요합니다).

TDatabaseRepository = class(TInterfacedObject, IRepository)
    function  SaveKeyValuePair(aKey: Integer; aValue: string): Boolean;
end;

클래스가 인터페이스를 구현할 때는 인터페이스에 선언 된 모든 메소드와 함수를 포함해야합니다. 그렇지 않으면 컴파일되지 않습니다.

주목할 가치가있는 한 가지 점은 호출자가 인터페이스로 작업 할 경우 액세스 수정자가 아무런 영향을 미치지 않는다는 것입니다. 예를 들어 인터페이스의 모든 기능은 strict private 멤버로 구현할 수 있지만 인터페이스 인스턴스가 사용되는 경우 다른 클래스에서 호출 할 수 있습니다.

다중 인터페이스 구현하기

클래스는 하나 이상의 인터페이스를 구현할 수 있으며, Delphi 클래스에서는 불가능한 둘 이상의 클래스 ( 다중 상속 )를 상속 하지 않습니다. 이를 위해 모든 인터페이스의 이름을 기본 클래스 뒤에 쉼표로 구분하여 추가해야합니다.

물론 구현 클래스는 각 인터페이스에 의해 선언 된 함수를 정의해야합니다.

IInterface1 = interface
    ['{A2437023-7606-4551-8D5A-1709212254AF}']
    procedure Method1();
    function Method2(): Boolean;
end;

IInterface2 = interface
    ['{6C47FF48-3943-4B53-8D5D-537F4A0DEC0D}']
    procedure SetValue(const aValue: TObject);
    function  GetValue(): TObject;

    property Value: TObject read GetValue write SetValue;
end;

TImplementer = class(TInterfacedObject, IInterface1, IInterface2)
    // IInterface1
    procedure Method1();
    function Method2(): Boolean;

    // IInterface2
    procedure SetValue(const aValue: TObject);
    function  GetValue(): TObject

    property Value: TObject read GetValue write SetValue;
end;

인터페이스 상속

인터페이스는 클래스처럼 정확하게 상속받을 수 있습니다. 따라서 구현 클래스는 인터페이스 및 모든 기본 인터페이스의 기능을 구현해야합니다. 그러나이 방법은 implenting 클래스가 기본 인터페이스를 구현한다는 것을 컴파일러가 알지 못하면 명시 적으로 나열된 인터페이스 만 알고 있습니다. 그렇기 as ISuperInterface 에서 TImplementer as ISuperInterface 사용 as ISuperInterface TImplementer 가 없습니다. 이는 또한 모든 기본 인터페이스를 명시 적으로 구현하는 일반적인 관행으로 이어집니다 (이 경우 TImplementer = class(TInterfacedObject, IDescendantInterface, ISuperInterface) ).

ISuperInterface = interface
    ['{A2437023-7606-4551-8D5A-1709212254AF}']
    procedure Method1();
    function Method2(): Boolean;
end;

IDescendantInterface = interface(ISuperInterface)
    ['{6C47FF48-3943-4B53-8D5D-537F4A0DEC0D}']
    procedure SetValue(const aValue: TObject);
    function  GetValue(): TObject;

    property Value: TObject read GetValue write SetValue;
end;

TImplementer = class(TInterfacedObject, IDescendantInterface)
    // ISuperInterface
    procedure Method1();
    function Method2(): Boolean;

    // IDescendantInterface
    procedure SetValue(const aValue: TObject);
    function  GetValue(): TObject

    property Value: TObject read GetValue write SetValue;
end;

인터페이스의 속성

인터페이스 변수의 선언이 불가능하기 때문에, 속성을 정의하는 "빠른"방법 ( property Value: TObject read FValue write FValue; )은 사용할 수 없습니다. 대신 Getter와 setter (필요한 경우에만 각각)를 인터페이스에서 선언해야합니다.

IInterface = interface(IInterface)
    ['{6C47FF48-3943-4B53-8D5D-537F4A0DEC0D}']
    procedure SetValue(const aValue: TObject);
    function  GetValue(): TObject;

    property Value: TObject read GetValue write SetValue;
end;

주목할 가치가있는 한 가지는 구현 클래스가 속성을 선언 할 필요가 없다는 것입니다. 컴파일러는 다음 코드를 허용합니다.

TImplementer = class(TInterfacedObject, IInterface)
    procedure SetValue(const aValue: TObject);
    function  GetValue(): TObject
end;

그러나 한가지주의 할 점은 클래스 자체를 통하지 않고 인터페이스의 인스턴스를 통해서만 속성에 액세스 할 수 있다는 것입니다. 또한 속성을 클래스에 추가하면 가독성이 높아집니다.



Modified text is an extract of the original Stack Overflow Documentation
아래 라이선스 CC BY-SA 3.0
와 제휴하지 않음 Stack Overflow