programing

Class.newInstance()가 "evil"인 이유는 무엇입니까?

newsource 2022. 10. 26. 21:04

Class.newInstance()가 "evil"인 이유는 무엇입니까?

Ryan Delucchi는 Tom Hawtin의 답변에 대한 코멘트 #3에서 다음과 같이 물었다.

Class.newInstance()가 "evil"인 이유는 무엇입니까?

코드 샘플에 대한 응답:

// Avoid Class.newInstance, for it is evil.
Constructor<? extends Runnable> ctor = runClass.getConstructor();
Runnable doRun = ctor.newInstance();

그럼 왜 '이블'일까요?

Java API 매뉴얼에서는 그 이유를 설명하고 있습니다(http://java.sun.com/javase/6/docs/api/java/lang/Class.html#newInstance()):

이 메서드는 체크된 예외를 포함하여 nullary constructor에 의해 느려진 예외를 전파합니다.이 메서드를 사용하면 컴파일러에 의해 실행되었을 컴파일 시간 예외 체크를 효과적으로 우회할 수 있습니다.Constructor.newInstance메서드는 컨스트럭터에 의해 발생한 예외를 (체크박스를 켜짐)로 래핑함으로써 이 문제를 회피합니다.InvocationTargetException.

즉, 체크된 예외 시스템을 없앨 수 있습니다.

또 하나의 이유:

최신 IDE를 사용하면 클래스 사용법을 찾을 수 있습니다.리팩터링 중에 사용자와 IDE가 변경하려는 클래스를 사용하는 코드를 알고 있으면 도움이 됩니다.

컨스트럭터를 명시적으로 사용하지 않고 Class.newInstance()를 사용하는 경우 리팩토링 중에 해당 사용을 찾을 수 없으며 컴파일 시 이 문제가 발생하지 않습니다.

왜 아무도 이에 대한 간단한 예를 제시하지 않았는지 모르겠다.Constructor::newInstance예를 들어, 마침내 Class::newInstance는 Java-9 이후 폐지되었습니다.

다음과 같은 매우 단순한 클래스가 있다고 가정합니다(고장은 문제가 되지 않습니다).

static class Foo {
    public Foo() throws IOException {
        throw new IOException();
    }
}

그리고 반성을 통해 그것의 인스턴스를 만들려고 합니다.첫번째Class::newInstance:

    Class<Foo> clazz = ...

    try {
        clazz.newInstance();
    } catch (InstantiationException e) {
        // handle 1
    } catch (IllegalAccessException e) {
        // handle 2
    }

이것을 호출하면,IOException던져지는 것 - 문제는 당신의 코드가 그것을 처리하지 않는다는 것입니다.handle 1도 아니다handle 2잡을 수 있을 거야

이와는 대조적으로 vs.a를 경유하여Constructor:

    Constructor<Foo> constructor = null;
    try {
        constructor = clazz.getConstructor();
    } catch (NoSuchMethodException e) {
        e.printStackTrace();
    }

    try {
        Foo foo = constructor.newInstance();
    } catch (InstantiationException e) {
        e.printStackTrace();
    } catch (IllegalAccessException e) {
        e.printStackTrace();
    } catch (InvocationTargetException e) {
        System.out.println("handle 3 called");
        e.printStackTrace();
    }

핸들 3이 호출되므로 사용자가 처리하도록 하겠습니다.

사실상,Class::newInstance예외 처리를 바이패스합니다(정말 원하지 않는 경우).

언급URL : https://stackoverflow.com/questions/195321/why-is-class-newinstance-evil