Является ли StringBuilder потокобезопасным (используя его с parallelStream)?
Мой код:
StringBuilder sb = new StringBuilder();
events.parallelStream().forEach(event -> {
sb.append(event.toString());
sb.append("\n");
});
Мне не нужен порядок events.toString()
в конечном результате. Но мне все равно, что events.toString()
будет правильно отображаться по одной строке за другой, без смешивания/перебора конечно.
Является ли parallelStream
(вместо stream
) безопасным в этом отношении?
Ответы
Ответ 1
Лучшее решение - использовать
events.parallelStream().map(event -> event+"\n").collect(Collectors.joining());
Или в качестве альтернативы (благодаря @Holger):
events.parallelStream().map(Object::toString).collect(Collectors.joining("\n", "", "\n"));
В общем случае избегайте использования forEach
в качестве терминальной операции для потоков. Обычно операции сокращения, такие как collect
или reduce
, являются лучшими альтернативами.
Ответ 2
Нет, он не является потокобезопасным.
Это основное различие между старыми StringBuffer
и новыми StringBuilder
- первые методы синхронизированы, а последние - нет.
Это не очень полезно сделать так, даже если вы вместо этого использовали бы StringBuffer
- потоки должны были бы ждать друг от друга, чтобы записать в StringBuffer
.
Ответ 3
Нет, это не так. Как отмечено в его javadoc:
Измененная последовательность символов. Этот класс предоставляет API, совместимый с StringBuffer, но без гарантии синхронизации.
Используйте StringBuffer
вместо этого.