В чем разница между instanceof и Class.isAssignableFrom (& hellip;)?

Мой python немного ржавый (любой может отредактировать этот код, чтобы внести исправления, если я каким-то образом испортил синтаксис), но здесь идет ....

def movingAverageExponential(values, alpha, epsilon = 0):

   if not 0 < alpha < 1:
      raise ValueError("out of range, alpha='%s'" % alpha)

   if not 0 <= epsilon < alpha:
      raise ValueError("out of range, epsilon='%s'" % epsilon)

   result = [None] * len(values)

   for i in range(len(result)):
       currentWeight = 1.0

       numerator     = 0
       denominator   = 0
       for value in values[i::-1]:
           numerator     += value * currentWeight
           denominator   += currentWeight

           currentWeight *= alpha
           if currentWeight < epsilon: 
              break

       result[i] = numerator / denominator

   return result

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

На конец функции, он меняет значения перед возвратом списка (чтобы они были в правильном порядке для вызывающего).

(SIDE ПРИМЕЧАНИЕ: если бы я использовал язык, отличный от python, я Сначала создайте полноразмерный пустой массив, а затем залейте его назад-порядок, чтобы мне не пришлось отменить его в конце. Но я не думаю, что вы можете объявить большой пустой массив в python. python list, добавление намного дешевле, чем добавление, поэтому я создал список в обратном порядке. Пожалуйста, исправьте меня, если я ошибаюсь.)

Аргумент «alpha» - это коэффициент распада на каждом итерация. Например, если вы использовали альфа 0,5, то сегодняшнее скользящее среднее значение будет состоять из следующих взвешенных значений:

today:        1.0
yesterday:    0.5
2 days ago:   0.25
3 days ago:   0.125
...etc...

Конечно, если у вас есть огромный массив значений, ценности от десяти или пятнадцати дней назад не будут вносить большой вклад в сегодняшнюю средневзвешенную. Аргумент «epsilon» позволяет вам установить точку отсечки, ниже которой вы перестанете заботиться о старых значениях (поскольку их вклад в сегодняшнее значение будет незначительным).

Вы вызывали бы функцию что-то вроде этого :

result = movingAverageExponential(values, 0.75, 0.0001)
432
задан Megamug 30 January 2009 в 19:44
поделиться

8 ответов

При использовании instanceof, необходимо знать класс B во время компиляции. При использовании isAssignableFrom() это может быть динамично и измениться во время времени выполнения.

471
ответ дан Andrew Tobilko 31 January 2009 в 05:44
поделиться

instanceof можно использовать только с ссылочными типами, но не с примитивными типами. isAssignableFrom() может использоваться с любыми объектами класса:

a instanceof int  // syntax error
3 instanceof Foo  // syntax error
int.class.isAssignableFrom(int.class)  // true

См. http://java.sun.com/javase/6/docs/api/java/. языки / Class.html # IsAssignableFrom (java.lang.Class) .

201
ответ дан Adam Rosenfield 30 January 2009 в 19:44
поделиться

Более прямым эквивалентом a instanceof B является

B.class.isInstance(a)

. Это работает (возвращает false), когда a равно null.

33
ответ дан user102008 30 January 2009 в 19:44
поделиться

Эта ветка дала мне некоторое представление о том, как instanceof отличается от isAssignableFrom, поэтому я решил поделиться чем-то своим.

Я обнаружил, что использование isAssignableFrom является единственным (возможно, не единственным, но, возможно, самым простым) способом спросить себя, может ли ссылка на один класс брать экземпляры другого, когда у одного есть экземпляры ни одного класса сделать сравнение.

Следовательно, я не нашел, что использование оператора instanceof для сравнения присваиваемости было бы хорошей идеей, когда у меня были только классы, если только я не собирался создавать экземпляр из одного из классов; Я думал, что это будет небрежно.

7
ответ дан jefflunt 30 January 2009 в 19:44
поделиться

Говоря с точки зрения производительности "2" (с JMH):

class A{}
class B extends A{}

public class InstanceOfTest {

public static final Object a = new A();
public static final Object b = new B();

@Benchmark
@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.NANOSECONDS)
public boolean testInstanceOf()
{
    return b instanceof A;
}

@Benchmark
@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.NANOSECONDS)
public boolean testIsInstance()
{
    return A.class.isInstance(b);
}

@Benchmark
@BenchmarkMode(Mode.AverageTime)
@OutputTimeUnit(TimeUnit.NANOSECONDS)
public boolean testIsAssignableFrom()
{
    return A.class.isAssignableFrom(b.getClass());
}

public static void main(String[] args) throws RunnerException {
    Options opt = new OptionsBuilder()
            .include(InstanceOfTest.class.getSimpleName())
            .warmupIterations(5)
            .measurementIterations(5)
            .forks(1)
            .build();

    new Runner(opt).run();
}
}

Это дает:

Benchmark                            Mode  Cnt  Score   Error  Units
InstanceOfTest.testInstanceOf        avgt    5  1,972 ? 0,002  ns/op
InstanceOfTest.testIsAssignableFrom  avgt    5  1,991 ? 0,004  ns/op
InstanceOfTest.testIsInstance        avgt    5  1,972 ? 0,003  ns/op

Таким образом, мы можем сделать вывод: instanceof так быстро, как isInstance () и isAssignableFrom () недалеко (+ 0,9% времени выполнения). Так что нет никакой разницы, что бы вы ни выбрали

0
ответ дан Yura 30 January 2009 в 19:44
поделиться

instanceof также не может использоваться с примитивными типами или универсальными типами. Как в следующем коде:

//Define Class< T > type ... 

Object e = new Object();

if(e instanceof T) {
  // Do something.
}

Ошибка: Невозможно выполнить проверку экземпляра для параметра типа T. Вместо этого используйте его объект стирания, так как дальнейшая информация общего типа будет удалена во время выполнения.

Не компилируется из-за удаления типа, удаляя ссылку на время выполнения. Тем не менее, код ниже будет скомпилирован:

if( type.isAssignableFrom(e.getClass())){
  // Do something.
}
3
ответ дан William Price 30 January 2009 в 19:44
поделиться

Рассмотрим следующую ситуацию. Предположим, вы хотите проверить, является ли тип A суперклассом типа obj, вы можете выбрать

... A.class.isAssignableFrom (obj.getClass ()) ...

ИЛИ

... экземпляр объекта A ...

Но решение isAssignableFrom требует, чтобы здесь был виден тип объекта. Если это не так (например, тип obj может относиться к частному внутреннему классу), этот параметр отключен. Однако решение instanceof всегда будет работать.

4
ответ дан 22 November 2019 в 23:09
поделиться

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

-2
ответ дан 22 November 2019 в 23:09
поделиться
Другие вопросы по тегам:

Похожие вопросы: