Случайное переопределение: следующие объявления имеют одну и ту же подпись JVM
Я получаю эту ошибку в Kotlin в этой части:
class GitHubRepoAdapter(private val context: Context,
private val values: List<GithubRepo>) : ArrayAdapter<GithubRepo>(context, R.layout.list_item,
values) {
частный контекст val: контекст
в журнале говорится:
Ошибка: (14, 25) Случайное переопределение: следующие объявления имеют одна и та же подпись JVM (getContext() Landroid/content/Context;): fun(): Контекст fun getContext(): Контекст!
Я не могу понять, что вызывает проблему.
Ответы
Ответ 1
Это происходит потому, что компилятор Kotlin пытается сгенерировать getter для val context
, объявленного в вашем основном конструкторе класса, а именно функцию getContext()
, но базовый класс ArrayAdapter<T>
уже имеет такую функцию.
Вы можете решить это, выполнив одно из следующих действий:
-
Измените параметр конструктора класса не как val
.
class GitHubRepoAdapter(context: Context, ...
В этом случае геттер не будет сгенерирован, и конфликт исчезнет.
Это, по-видимому, предпочтительное решение в вашем случае, потому что даже без переоценки уже существует синтетическое свойство context
, полученное от Java getter.
-
Используйте @JvmName
аннотация, применить ее к context
свойство getter:
class GitHubRepoAdapter(@get:JvmName("getContext_") private val context: Context, ...
Это заставит компилятор сгенерировать геттер с другим именем JVM (тем, который указан в аннотации), что позволит избежать конфликта, но сделать его доступным с Java менее интуитивным (тем более, что будут две аналогичные функции). В Котлине вы все равно сможете использовать свойство с его первоначальным именем context
.
Ответ 2
В дополнение к уже предоставленному ответу...
- Или вы можете сохранить
val
(или var
), но изменить имя параметра на то, что не сталкивается с объявлением суперкласса.
В объявлении класса параметры в объявлениях конструктора часто больше, чем просто параметры. Используя val
или var
, вы фактически объявляете элементы свойств (а не только параметры). И вместе с членами собственности появляются автоматические "геттеры" (и "сеттеры" в случае var
). Автоматический приемник в случае OP называется getContext()
, но базовый класс уже имеет getContext() (та же подпись).
Скорее всего, целью здесь было просто передать context
супер, и в этом случае другой ответ лучше всего работает. Но в случае, когда требуется новое свойство, но выбранное имя сталкивается с другим назначенным членом супер, изменение имени является альтернативой.
Короче, изменение имени применяется, когда делать требуется новая переменная участника , но суперкласс уже предоставляет другому члену то же имя.