Хабр Курсы для всех
РЕКЛАМА
Практикум, Хекслет, SkyPro, авторские курсы — собрали всех и попросили скидки. Осталось выбрать!
It prevents the field being a compile time constant.
References to final String fields which are compile time constants are compiled as a literal, not as an access to the field.
In the example, if there was no .intern(), anything referencing the library would have to be recompiled when the value of the schema namespace is updated. So the authors added 'intern()', making the value not a compile time constant, so the client code desn't have to be rebuilt whhen the library is updated.
Object get(String name) {
Object res = cache.get(name);
if(res == null) {
res = createElement(name);
if(res != null) cache.put(name);
}
return res;
}createElement) долгое и ресурсоёмкое и при этом сразу несколько тредов могут запросить создание одного и того же объекта одновременно (то есть пока один тред обрабатывает createElement, другой снова заходит в этот get и тоже приступает к createElement, потому что объекта ещё нет в кэше). Добавил в объявление метода get волшебное слово synchronized, но стало ещё хуже, потому что если один тред создаёт долгий элемент, то другие ждут его, хотя они запросили совсем другой быстрый элемент. То есть синхронизация нужна только при запросе одного и того же элемента. Обернул тело функции в блок synchronized(name) {}, но это не сработало. Тут я вспомнил, что что-то такое недавно читал на Хабре :-) Изменил на synchronized(name.intern()) {}. После этого как будто бы стало всё прекрасно, так что автору спасибо за подсказку :-) Интересно, это правильное решение задачи или есть подводные камни, о которых я не подумал?Если кто забредёт сюда, не читайте этот бред выше, который я восемь лет назад написал. Был маленький, глупый.
Все о String.intern()