programing

자바 제네릭스의 'E', 'T', '?'의 차이점은 무엇입니까?

newsource 2022. 7. 30. 20:53

자바 제네릭스의 'E', 'T', '?'의 차이점은 무엇입니까?

자바 코드는 다음과 같습니다.

public interface Foo<E> {}

public interface Bar<T> {}

public interface Zar<?> {}

위의 세 가지 모두 차이점은 무엇이며 Java에서는 이러한 유형의 클래스 또는 인터페이스 선언을 뭐라고 합니까?

처음 두 개에는 차이가 없습니다. 유형 매개 변수에 서로 다른 이름을 사용할 뿐입니다.E ★★★★★★★★★★★★★★★★★」T를 참조해 주세요.

?는 type 인수를 지정할 때 사용되는 와일드카드로 사용됩니다.List<?> foo = ... foo어떤 종류의 목록을 가리키지만 그게 뭔지는 모릅니다

이 모든 것은 제네릭이며, 꽤 큰 주제입니다.물론 더 많은 정보를 얻을 수 있지만, 다음 자료를 통해 정보를 얻을 수 있습니다.

다른 어떤 것보다도 관습에 가깝습니다.

  • T is is is is is is 。
  • E는 Element 「 「 「」 「」 )가 것을 의미합니다.List<E>) : 요소 목록)
  • K(단위는) 열쇠입니다)Map<K,V>
  • V Value는 Value('값')입니다.

이 두 값은 완전히 호환됩니다(같은 선언에서 모순됨).

앞의 답변에서는 타입 파라미터(T, E 등)에 대해 설명하고 있습니다만, 와일드카드 「?」나 그 차이는 설명하지 않기 때문에 대응하겠습니다.

우선 확실히 하기 위해 와일드카드 파라미터와 타입 파라미터가 다릅니다.의 유형을 변수를 들어에는 정의되지 에 할 수 있는 의 허용 한 타입이 정의되어 있습니다.와일드카드에는 정의되지 않습니다.와일드카드에서는 범용 타입에 사용할 수 있는 허용 가능한 타입의 세트만 정의됩니다.없다(도 없이)extends ★★★★★★★★★★★★★★★★★」super와일드카드는 "여기에 있는 모든 유형을 사용"을 의미합니다.

와일드카드는 항상 꺽쇠 괄호 사이에 있어 범용 타입의 컨텍스트에서만 의미가 있습니다.

public void foo(List<?> listOfAnyType) {...}  // pass a List of any type

절대.

public <?> ? bar(? someType) {...}  // error. Must use type params here

또는

public class MyGeneric ? {      // error
    public ? getFoo() { ... }   // error
    ...
}

겹치는 부분이 더 헷갈려요.예를 들어 다음과 같습니다.

List<T> fooList;  // A list which will be of type T, when T is chosen.
                  // Requires T was defined above in this scope
List<?> barList;  // A list of some type, decided elsewhere. You can do
                  // this anywhere, no T required.

방법 정의와 가능한 것은 많은 중복이 있습니다.다음은 기능적으로 동일합니다.

public <T> void foo(List<T> listOfT) {...}
public void bar(List<?> listOfSomething)  {...}

그렇다면, 겹치는 부분이 있다면, 왜 둘 중 하나를 사용해야 합니까?경우에 따라서는 형식 파라미터가 필요 없는 경우 와일드카드를 사용하여 코드를 심플하게/가독성을 높여야 한다고 말하는 사람도 있습니다.위에서 설명한 주요 차이점 중 하나는 type params는 스코프 내의 다른 곳에서 사용할 수 있는 유형 변수(예를 들어 T)를 정의합니다.Wildcard는 정의하지 않습니다.그 이외의 경우 유형 파라미터와 와일드카드 사이에는 다음 두 가지 큰 차이가 있습니다.

유형 매개 변수는 여러 개의 경계 클래스를 가질 수 있지만 와일드카드에는 다음을 포함할 수 없습니다.

public class Foo <T extends Comparable<T> & Cloneable> {...}

와일드카드에는 하한을 지정할 수 있습니다.유형 파라미터는 다음과 같이 설정할 수 없습니다.

public void bar(List<? super Integer> list) {...}

상기의 경우List<? super Integer>정의하다Integer와일드카드 하한으로 지정합니다.즉, 리스트타입은 Integer 또는 Integer의 슈퍼타입이어야 합니다.범용 타입의 바운딩은 제가 상세하게 다루고 싶은 범위를 넘어섰습니다.즉, 범용 타입을 정의할 수 있습니다.이것에 의해 제네릭스를 다형적으로 취급할 수 있습니다.예:

public void foo(List<? extends Number> numbers) {...}

합격할 수 있습니다.List<Integer>,List<Float>,List<Byte>, 등numbers타입 바운딩이 없으면, 이것은 동작하지 않습니다.그게 제네릭스의 특징입니다.

마지막으로 와일드카드를 사용하여 다른 방법으로는 할 수 없다고 생각되는 작업을 수행하는 메서드의 정의를 다음에 나타냅니다.

public static <T extends Number> void adder(T elem, List<? super Number> numberSuper) {
    numberSuper.add(elem);
}

numberSuper는 번호 리스트 또는 슈퍼타입 번호(예:List<Object>, 및elemNumber 또는 임의의 서브타입이어야 합니다.모든 바운딩에 의해 컴파일러는 다음과 같이 확신할 수 있습니다..add()타입이 안전합니다.

A형 변수,<>지정하는 T>,이 될 수 있non-primitive 형식:클래스 형식, 인터페이스 형식, 배열 형식, 또는 심지어 다른 형식 변수.

가장 일반적으로 사용되는 유형 매개 변수 이름: 있다.

  • E-원소(광범위하게는 자바 Collections Framework에서 사용되).
  • K - 키
  • N - 번호
  • T - 유형
  • V - 값

자바 7에서 이렇게 초기화할:허용된다.

Foo<String, Integer> foo = new Foo<>(); // Java 7
Foo<String, Integer> foo = new Foo<String, Integer>(); // Java 6

가장 일반적으로 사용되는 유형 매개 변수 이름: 있다.

E - Element (used extensively by the Java Collections Framework)
K - Key
N - Number
T - Type
V - Value
S,U,V etc. - 2nd, 3rd, 4th types

이 이름은 JavaSEAPI에서 사용되는지 볼게요.

때도 이와 같은 기능을 설명 컴파일러:각각의 와일드 카드(예:목록에 물음표)에 대한 포획을 할 것이다.

foo(List<?> list) {
    list.put(list.get()) // ERROR: capture and Object are not identical type.
}

하지만 V 같은 유형과 해당 제네릭을 만드는 법.: 괜찮을 것이다.

<V>void foo(List<V> list) {
    list.put(list.get())
}

언급URL:https://stackoverflow.com/questions/6008241/what-is-the-difference-between-e-t-and-for-java-generics