Подтвердить что ты не робот

Как измерить скорость кода, написанного на Java? (Алгоритмы AI)

Как измерить скорость кода, написанного на Java?

Я планирую разработать программное обеспечение, которое решит Sudoku, используя все доступные в настоящее время алгоритмы AI и ML и сравните время с простым методом грубой силы. Мне нужно измерить время каждого алгоритма, я хотел бы попросить предложения о том, что это лучший способ сделать это? Очень важно, чтобы программа была полезной на любой машине, независимо от мощности процессора/памяти.

Спасибо.

4b9b3361

Ответ 1

Как было предложено другими, System.currentTimeMillis() неплохо, но обратите внимание на следующие оговорки:

  • System.currentTimeMillis() измеряет пройденное физическое время ( "время настенных часов" ), а не время процессора. Если на машине запущены другие приложения, ваш код получит меньше CPU, и его скорость будет уменьшаться. Итак, скамейка только в других системах бездействия.
  • Аналогично, многопоточное приложение в многоядерной системе может получить дополнительный скрытый ЦП. Истекшая временная мера не отражает всю сложность многопоточных приложений.
  • Java требует немного "разминки". Сначала VM интерпретирует код (который медленный), и, если данный метод используется слишком много раз, тогда компилятор JIT переведет метод на собственный код. Только в этот момент метод достигнет максимальной скорости. Я рекомендую вам выполнить несколько "пустых циклов" перед вызовом System.currentTimeMillis().
  • Точность System.currentTimeMillis() редко составляет 1 мс. Во многих системах точность не превышает 10 мс или даже больше. Кроме того, JVM иногда запускает GC, вызывая заметные паузы. Я предлагаю вам организовать вашу меру в цикле и настаивать на работе в течение как минимум нескольких секунд.

Это дает следующий код:

for (int i = 0; i < 10; i ++) {
    runMethod();
}
int count = 10;
for (;;) {
    long begin = System.currentTimeMillis();
    for (int i = 0; i < count; i ++)
        runMethod();
    long end = System.currentTimeMillis();
    if ((end - begin) < 10000) {
        count *= 2;
        continue;
    }
    reportElapsedTime((double)(end - begin) / count);
}

Как видите, первые десять "пустых" запусков. Затем программа запускает метод в цикле столько раз, сколько необходимо, так что цикл занимает не менее десяти секунд. Десять секунд должно быть достаточно, чтобы сгладить прогоны GC и другие неточности системы. Когда я реализую реализацию хэш-функции скамейки, я использую две секунды, и даже несмотря на то, что сама функция не вызывает никакого выделения памяти, я все равно получаю изменения до 3%.

Ответ 2

Я обычно использую

System.currentTimeMillis()

для вычисления дельт времени:

long start = System.currentTimeMillis();
/* do your algorithm iteration */
long elapsed = System.currentTimeMillis() - start;

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

EDIT: есть альтернатива делать то же самое с System.nanoTime(), но у вас нет гарантии, что точность будет равна наносекундам.

Ответ 3

Это другой способ (с наносекундами)

long nanos = System.nanoTime();
// execute your stuff
long duration = System.nanoTime() - nanos;
int seconds = (int) (duration / 1000000000);
int milliseconds = (int) (duration / 1000000) % 1000;
int nanoseconds = (int) (duration % 1000000);
System.out.printf("%d seconds, %d milliseconds en %d nanoseconds\n", seconds, milliseconds, nanoseconds);

Наносы являются дополнительными, но приятными.

Ответ 4

Если вы заинтересованы в большой точности измерений, вы должны измерить время процессора, а не "настенные часы". Таким образом, вы не будете измерять время, которое ОС проводит, делая что-то еще. Чтобы измерить это время, вы можете посмотреть Java, сравнивающий время процессора

Ответ 5

Несмотря на то, что все ответы здесь действительны, я бы предложил, чтобы измерение реального времени не могло быть полностью релевантным вашей цели, то есть сравнивать и сравнивать различные алгоритмы поиска, чтобы найти "лучший". В этом случае гораздо проще подсчитать количество узлов, которые вы выполняете. Хотя хорошо также знать время выполнения, есть много шума, так как каждый алгоритм может поразить CPU/cache/memory/disk определенным образом. Измеряя узлы, вы смотрите на самую важную меру того, насколько хорош алгоритм поиска, поскольку чем меньше узлов он ищет, тем быстрее он найдет ответ.