В чем разница между a.getClass() и A.class на Яве?



в Java какие плюсы/минусы существуют вокруг выбора использовать a.getClass() или A.class? Либо может быть использован везде, где Class<?> ожидается, но я предполагаю, что будет производительность или другие тонкие преимущества для использования обоих в разных обстоятельствах (так же, как и с Class.forName() и ClassLoader.loadClass().

527   6  

6 ответов:

Я бы не стал сравнивать их с точки зрения плюсов/минусов, поскольку у них разные цели, и редко есть "выбор" между ними.

  • a.getClass() возвращает времени выполнения типа на a. То есть, если у вас A a = new B(); затем a.getClass() вернет B класса.

  • A.class оценивает в A класс статически, и используется для других целей, часто связанных с отображение.

С точки зрения производительности, есть мая быть измеримой разницей, но я ничего не скажу об этом, потому что в конце концов это зависит от JVM и/или компилятора.


этот пост был переписан как статья здесь.

они на самом деле отличаются в отношении которых их можно использовать. A.class работает во время компиляции, в то время как a.getClass() требуется экземпляр типа A и работает во время выполнения.

там может быть разница в производительности, а также. В то время как A.class может быть решена компилятором, потому что он знает фактический тип A,a.getClass() это виртуальный вызов метода происходит во время выполнения.

для справки, компилятор, ориентированный на байт-код, обычно выдает следующее инструкции для Integer.getClass():

aload_1
invokevirtual   #3; //Method java/lang/Object.getClass:()Ljava/lang/Class;

и следуя по Integer.class:

//const #3 = class  #16;    //  java/lang/Integer

ldc_w   #3; //class java/lang/Integer

первый обычно включает в себя отправку виртуального метода и, следовательно, предположительно занимает больше времени для выполнения. То есть в конце виртуальной Java-машины, зависит от однако.

посмотрите на примеры ниже

a.getClass()!= A.class, т. е. a не является экземпляром A, но анонимного подкласса а

a.getClass() требуется экземпляр типа A

использовать a.getClass когда у вас есть экземпляр класса/типа и вы хотите получить точный тип его. в то время как a.class используется, когда у вас есть type доступен и вы хотите создать его экземпляр.
Также getClass() возвращает типом времени выполнения экземпляра, а .class вычисляется во время компиляции.
Учитывая производительность getClass() и.class,.class имеет высокую производительность, чем getClass() .
пример :

public class PerfomanceClass {

    public static void main(String[] args) {
        // TODO Auto-generated method stub

        long time=System.nanoTime();
        Class class1="String".getClass();
        class1="String".getClass();
        class1="String".getClass();
        class1="String".getClass();

        System.out.println("time (getClass()) :"+(System.nanoTime()-time)+" ns");     


        long time2=System.nanoTime();
        Class class2=String.class;
        class2=String.class;
        class2=String.class;
        class2=String.class;

        System.out.println("time (.class):"+(System.nanoTime()-time2)+" ns");
    }

}

выход :

time (getClass()) : 79410 ns
time (.class)     : 8032 ns

есть одно отличие я хотел бы добавить. Допустим, у вас есть конструктор класса a, как показано ниже, с суперклассом, который принимает объект класса. Вы хотите, чтобы всякий раз, когда создается объект подкласса, объект класса подкласса должен быть передан суперклассу. Ниже код не будет компилироваться, так как вы не можете вызвать метод экземпляра в конструкторе. В том случае, если вы замените myObject.getClass() С MyClass.class. Он будет работать отлично.

Class MyClass
{
    private MyClass myObject = new MyClass();
    public MyClass()
    {
        super(myObject.getClass()); //error line compile time error
    }
}

интересно, что различия в производительности, упомянутых в приведенном выше примере, по-видимому, связаны с другими причинами. Используя 3 разных класса, в среднем производительность будет почти одинаковой:

import java.util.LinkedHashMap;
public class PerfomanceClass {

public static void main(String[] args) {

    long time = System.nanoTime();
    Class class1 = "String".getClass();
    Class class11 = "Integer".getClass();
    Class class111 = "LinkedHashMap".getClass();

    System.out.println("time (getClass()) :" + (System.nanoTime() - time) + " ns");

    long time2 = System.nanoTime();
    Class class2 = String.class;
    Class class22 = Integer.class;
    Class class222 = LinkedHashMap.class;

    System.out.println("time (.class):" + (System.nanoTime() - time2) + " ns");
} }

выход будет что-то вроде :

time (getClass()) :23506 ns 
time (.class):23838 ns

и переключение порядка вызовов даже приведет к getClass() быть быстрее.

import java.util.LinkedHashMap;

public class PerfomanceClass {

public static void main(String[] args) {
    long time2 = System.nanoTime();
    Class class2 = LinkedHashMap.class;

    System.out.println("time (.class):" + (System.nanoTime() - time2) + " ns");

    long time = System.nanoTime();
    Class class1 = "LinkedHashMap".getClass();

    System.out.println("time (getClass()) :" + (System.nanoTime() - time) + " ns");
}}

выход:

time (.class):33108 ns
time (getClass()) :6622 ns

Comments

    Ничего не найдено.