programing

Java 제네릭 T 대 객체

nicescript 2022. 9. 21. 22:24
반응형

Java 제네릭 T 대 객체

다음 두 가지 메서드 선언의 차이점은 무엇입니까?

public Object doSomething(Object obj) {....}

public <T> T doSomething(T t) {....}

한쪽은 할 수 있지만 다른 한쪽은 할 수 없는 일이 있습니까?이 사이트에서는 이 질문을 찾을 수 없었습니다.

문맥에서 분리됨 - 차이가 없습니다.둘 다t그리고.obj의 메서드만 호출할 수 있습니다.Object.

그러나 컨텍스트에서는 일반 클래스가 있는 경우:

MyClass<Foo> my = new MyClass<Foo>();
Foo foo = new Foo();

그 후, 다음과 같이 입력합니다.

Foo newFoo = my.doSomething(foo);

객체와 동일한 코드

Foo newFoo = (Foo) my.doSomething(foo);

두 가지 장점:

  • 캐스팅 불필요(컴파일러는 이것을 숨김)
  • 동작하는 시간 안전성을 컴파일합니다.이 경우,Object버전이 사용되고 있기 때문에 메서드가 항상 반환되는 것은 아닙니다.Foo. 다시 돌아오면Bar, 를 취득할 수 있습니다.ClassCastException, 실행 시.

여기서의 차이점은 첫 번째에서는 발신자가 오브젝트인스턴스(모든 클래스)를 전달해야 하며, 발신자가 다른 오브젝트(같은 타입일 필요는 없는 모든 클래스)를 반환하도록 지정하는 것입니다.

두 번째로 반환되는 유형은 클래스 정의 시 지정된 유형과 동일합니다.

Example ex = new Example<Integer>();

여기서는 클래스 또는 메서드에 더 많은 제약을 가할 수 있는 타입 T를 지정합니다.예를 들어, VIP를 인스턴스화할 수 있습니다.LinkedList<Integer>또는LinkedList<Example>이러한 메서드 중 하나를 호출하면 Integer 또는 Example 인스턴스가 반환됩니다.

여기서의 주된 목표는, 타입 캐스팅에 의존하지 않고, 클래스가 동작하는 오브젝트의 타입을 발신 코드가 지정할 수 있는 것입니다.

Oracle의 Java Generics*를 참조하십시오.

* 갱신된 링크.

차이점은 일반적인 방법에서는 캐스팅할 필요가 없고 잘못하면 컴파일 오류가 발생한다는 것입니다.

public class App {

    public static void main(String[] args) {

        String s = process("vv");
        String b = process(new Object()); // Compilation error
    }

    public static <T> T process(T val) {

        return val;
    }
}

항상 캐스팅해야 하는 오브젝트를 사용하여 잘못해도 오류가 발생하지 않습니다.

public class App {

    public static void main(String[] args) {

        String s = (String)process("vv");
        String b = (String)process(new Object());
    }

    public static Object process(Object val) {

        return val;
    }
}

추가 수업 섭외는 필요 없습니다.첫 번째 경우 항상 java.lang 클래스의 오브젝트를 얻을 수 있습니다.클래스에게 던져야 하는 오브젝트.두 번째 경우 T는 일반 서명에 정의된 클래스로 대체되며 클래스 캐스팅이 필요하지 않습니다.

런타임에는 아무것도 없습니다.그러나 컴파일 시 두 번째 예에서는 파라미터의 유형과 반환값의 유형이 T가 해결한 유형과 일치하는지(또는 하위 유형인지) 확인하기 위해 유형 검사를 수행합니다(첫 번째 예에서는 유형 검사도 수행하지만 모든 개체는 개체의 하위 유형이므로 모든 유형이 허용됩니다).

T는 범용 타입입니다.즉, 실행 시 수식 개체로 대체될 수 있습니다.다음과 같은 메서드를 호출할 수 있습니다.

String response = doSomething("hello world");

또는

MyObject response = doSomething(new MyObject());

또는

Integer response = doSomething(31);

보시다시피 여기 다형성이 있어요.

그러나 오브젝트를 반환하도록 선언된 경우 캐스팅을 입력하지 않으면 이 작업을 수행할 수 없습니다.

첫 번째 경우 string과 같은 임의의 유형의 파라미터를 사용하여 foo 유형을 반환합니다.두 번째 경우 유형 foo의 매개 변수를 사용하고 유형 foo의 개체를 반환합니다.

Java에서 Generics over Object type을 고려할 수 있는 이유는 다음과 같습니다.

  1. 제네릭스는 유연하고 안전합니다.동시에 타입 캐스팅을 필요로 하는 오브젝트로 작업하면 오류가 발생하기 쉽습니다.
  2. Java에서의 Type Casting은 느린 참조: [1]: https://www.infoworld.com/article/2076555/java-performance-programming--part-2--the-cost-of-casting.html

언급URL : https://stackoverflow.com/questions/5207115/java-generics-t-vs-object

반응형