문제

다음을 수행하십시오.

public Class<List<String>> getObjectType() {
    // what can I return here?
}

제네릭을 만족시키고 컴파일하는이 방법에서 어떤 클래스 리터럴 표현식을 반환 할 수 있습니까? List.class 컴파일하지 않으며 그럴 것도 없습니다 List.<String>class.

"왜"가 궁금하다면, 나는 Spring 's 구현을 쓰고 있습니다. FactoryBean<List<String>>,이를 구현해야합니다 Class<List<String>> getObjectType(). 그러나 이것은입니다 ~ 아니다 봄 질문.

편집하다: Springsource에있는 권력에 의해 내 평범한 울음 소리가 들렸으므로 Spring 3.0.1은 반환 유형을 가질 것입니다. getObjectType() 바뀌었다 Class<?>, 문제를 깔끔하게 피합니다.

도움이 되었습니까?

해결책

당신은 항상 당신이 필요로하는 것에 캐스트 할 수 있습니다.

return (Class<List<String>>) new ArrayList<String>().getClass();

또는

return (Class<List<String>>) Collections.<String>emptyList().getClass();

그러나 나는 그것이 당신이 추구하는 것이 아니라고 생각합니다. 글쎄, 그것은 경고와 함께 작동하지만 정확히 "아름다운"것은 아닙니다.

방금 이것을 찾았습니다

와일드 카드 매개 변수화 유형에 대한 클래스 리터럴이없는 이유는 무엇입니까?

와일드 카드 매개 변수화 유형에는 정확한 런타임 유형 표현이 없기 때문입니다.

따라서 캐스팅이 유일한 방법 일 수 있습니다.

다른 팁

구조물을 사용해서는 안됩니다 Class<List<String>>. 그것은 무의미하며 Java에서 경고를 생성해야합니다 (그러나 그렇지는 않습니다). 클래스 인스턴스는 항상 원시 유형을 나타내므로 Class<List>; 그게 다야. 당신이 무언가를 원한다면, List<String>, Guice가 사용하는 것처럼 "슈퍼 타입 토큰"이 필요합니다.

http://google-guice.googlecode.com/git/javadoc/com/google/inject/typeliteral.html

a의 존재 Class<List<String>> 본질적으로 위험합니다. 이유는 다음과 같습니다.

// This statement generates a warning - for a reason...
Class<List<String>> unsafeListClass = (Class<List<String>>) (Class<?>) List.class;

List<Integer> integerList = new ArrayList<Integer>(); // Ok
integerList.add(42); // Ok

System.out.println(unsafeListClass.isInstance(integerList)); // Prints "true".
List<String> stringList =
   unsafeListClass.cast(integerList); // Succeeds, with no warning!
stringList.add("Hello, World!"); // Also succeeds with no warning

for (int x: integerList) {
    // Compiles without warning, but throws ClassCastException at runtime
    System.out.println(100-x);
}

설립하다 이 링크 SpringFramework.org에서 통찰력을 제공합니다.

예를 들어

List<String> myList = new ArrayList<String>();
return (Class<List<String>>)myList.getClass();

다음과 같은 방법을 구현할 수 있습니다.

public Class<List<String>> getObjectType() {
    return (Class<List<String>>) ((Class)List.class);
}

태양 포럼 에서이 토론을 확인하십시오.

http://forums.sun.com/thread.jspa?threadid=5253007

"Super Type Tokens"를 사용하여 주변의 작업을 설명하는 참조 된 블로그 게시물 :

http://gafter.blogspot.com/2006/12/super-type-tokens.html

어떤 클래스 리터럴이 편집 될 것이기 때문에 이것이 전혀 가능한지 확실하지 않습니다. Class.forName(...) 그리고 런타임에 이런 일이 발생하기 때문에 일반적인 정보가 남아 있지 않습니다.

확실하지 않지만 다음 질문은 당신과 관련이있을 수 있습니다 ...

Java Generics 유형 매개 변수 및 해당 유형의 작업

이건 어때 :

public class TestMain {
    public static void main(String[] args) throws Exception {
        Type type = TestMain.class.getMethod("dummy").getGenericReturnType();
        System.out.println("type = " + type);
    }

    public List<Integer> dummy() {return null;}
}

이 인쇄물 :

type = java.util.List<java.lang.Integer>

다음은 문제가 있습니다.

> public Class<List<String>> getModelType() {
>   return (Class<List<String>>) new ArrayList<String>().getClass();
> }

예 : 객체가 유형에 대해 말하는지 테스트하고 싶다면

org.eclipse.emf.common.util.BasicEList<String> 

유형입니다

List<String> 

위에서 언급 한 getModelType () 접근법의 결과를 기반으로합니다.

BasicEList<String> fromObject = ...;
if (getModelType().isAssignableFrom(fromObject.getClass())) {
    transferFromModelToUi(getModelType().cast(fromObject));
}

두 객체가 인터페이스 목록을 구현하기 때문에 False가 발생하지만 (getModelType ()가 ArrayList가 아닌 유형 목록의 클래스 객체를 반환하기 때문에).

다음은 나에게 효과가있는 접근법이 있습니다 (약간 번거롭지 만 위의 예에서 올바른 결과로 이어지면 정적 이니셜 라이저로 이동할 수 있음).

public Class<List<String>> getModelType() {
    Class<?> arrayListClass = new ArrayList<String>().getClass();
    Class<?>[] interfaces = arrayListClass.getInterfaces();
    int index = 0;
    for (int i = 0; i < interfaces.length; i++) {
        if (interfaces[i].equals(List.class)) {
            index = i;
            break;
        }
    }
    return (Class<List<String>>) interfaces[index];
}
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top