Да, a val
, хранящийся в companion object
, является более эффективным. Вы можете использовать Kotlin bytecode viewer, чтобы узнать, с чем скомпилированы эти параметры.
Вот вещи, которые я заметил, что может повлиять на производительность:
Companion объект val
хранится только один раз, в отличие, например val
, который фактически хранится в каждом отдельном случае, таким образом, увеличивая след экземпляры памяти (String
буквального is stored in constant pool, но экземпляр будет иметь ссылку на него) и время создания экземпляра (во время построения поле должно быть заполнено).
Доступ к сопутствующему объекту val
несколько раз подряд лучше работает с кэшем ЦП, чем с использованием val
в разных экземплярах: он имеет лучшие locality of reference. Выделение разным экземплярам для доступа к val
в них, скорее всего, приведет к промахам кэш-памяти CPU, что плохо для производительности.
Однако, если val
используется только внутри методов экземпляра одного и того же класса, описанный эффект вряд ли влияет на производительность, поскольку методы, скорее всего, разыменовать this
в любом случае, и это может даже работать лучше, не вызывая вероятный промах кэша при доступе сопутствующий объект.
Добавление @JvmStatic
делает доступ немного быстрее. Без него доступ к значению требует получения статического Companion
ссылки и вызова getSOME_CONST()
на нем. С @JvmStatic
будет установлен статический метод getSOME_CONST()
(пропуская Companion
). Также есть @JvmField
, который создает публичное поле, к которому можно получить доступ напрямую, даже не называя getter.
Но JIT-компилятор, скорее всего, оптимизирует доступ к геттеру в первых двух случаях, так что эффект аннотаций будет едва заметен.
Кроме того, помимо производительности, экземпляр val
имеет семантику значения, которое может быть различным для каждого экземпляра, так companion object
, кажется, соответствует случаю глобальной постоянной величины лучше.
Вы можете использовать автономный объект для констант, не обязательно компаньон;) – voddan