Почему Thread.sleep (0) может предотвратить gc в rocketmq? - PullRequest
0 голосов
/ 13 ноября 2018

Недавно я прочитал исходный код в RocketMQ, но не могу понять этот код. Почему этот код может помешать gc?

https://github.com/apache/rocketmq/blob/master/store/src/main/java/org/apache/rocketmq/store/MappedFile.java

for (int i = 0, j = 0; i < this.fileSize; i += MappedFile.OS_PAGE_SIZE, j++) {
        byteBuffer.put(i, (byte) 0);
        // force flush when flush disk type is sync
        if (type == FlushDiskType.SYNC_FLUSH) {
            if ((i / OS_PAGE_SIZE) - (flush / OS_PAGE_SIZE) >= pages) {
                flush = i;
                mappedByteBuffer.force();
            }
        }

        // prevent gc
        if (j % 1000 == 0) {
            log.info("j={}, costTime={}", j, System.currentTimeMillis() - time);
            time = System.currentTimeMillis();
            try {
                Thread.sleep(0);
            } catch (InterruptedException e) {
                log.error("Interrupted", e);
            }
        }
 }

1 Ответ

0 голосов
/ 13 ноября 2018

Это не так.

Только в документации по сну потока:

Заставляет текущий выполняющийся поток в спящий режим (временно прекращать выполнение) на указанное количество миллисекунд, в зависимости от точности и точности системных таймеров и планировщиков. Поток не теряет права собственности ни на какие мониторы.

Что это значит может оказать побочный эффект на поведение сборщика мусора.

Вызывая Thread.sleep(0), вы (потенциально (это 0, так что реализация может даже игнорировать это)) переключают контекст, и вместо этого можно выбрать параллельный поток GC, чтобы очистить другие ссылки , Незначительный побочный эффект заключается в том, что вы потенциально чаще запускаете GC - что может помешать длительным сборкам мусора (вы увеличиваете вероятность запуска GC каждые 1000 итераций).

...