102 votes

Contournement accidentel : Les déclarations suivantes ont la même signature JVM

J'ai une erreur dans Kotlin dans cette partie :

class GitHubRepoAdapter(
    private val context: Context,
    private val values: List<GithubRepo>
) : ArrayAdapter<GithubRepo>(
    context, 
    R.layout.list_item,
    values
)

private val context: Context

Dans le journal, il est écrit :

Error:(14, 25) Accidental override: The following declarations have the same JVM signature
(getContext()Landroid/content/Context;):  
    fun <get-context>(): Context  
    fun getContext(): Context!

Je ne suis pas en mesure de voir ce qui cause le problème.

1 votes

Cela pourrait être utile stackoverflow.com/questions/29268526/

127voto

hotkey Points 119

Cela se produit parce que le compilateur Kotlin essaie de générer un getter pour val context déclarée dans le constructeur primaire de votre classe, à savoir une méthode getContext() mais la classe de base ArrayAdapter<T> dispose déjà d'une telle méthode .

Vous pouvez résoudre ce problème en faisant l'une des choses suivantes :

  • Changez le paramètre du constructeur de votre classe pour ne pas être un val .

     class GitHubRepoAdapter(context: Context, ...

    Dans ce cas, le getter ne sera pas généré, et le conflit sera résolu.

    Cela semble être la solution préférable dans votre cas, car, même sans redéclaration, il existe déjà une propriété synthétique context déduit du getter Java .

  • Utilisez le @JvmName annotation, l'appliquer à la context récepteur de propriété :

     class GitHubRepoAdapter(@get:JvmName("getContext_") private val context: Context, ...

    Le compilateur générera ainsi le getter avec un autre nom JVM (celui spécifié dans l'annotation), ce qui évitera le conflit, mais rendra son accès depuis Java moins intuitif (d'autant plus qu'il y aura deux fonctions similaires). En Kotlin, vous pourrez toujours utiliser la propriété avec son nom original context .

43voto

Les Points 2432

En plus de la réponse déjà donnée...

  • Ou, vous pouvez garder val (ou var ) mais changez le nom du paramètre en quelque chose qui n'entre pas en collision avec la déclaration de la super classe.

Dans une déclaration de classe, les paramètres des déclarations de constructeur sont souvent plus que de simples paramètres. Utilisation de val ou var vous déclarez en fait des membres de propriété (et pas seulement des paramètres). Et avec les membres de la propriété viennent des "getters" automatiques (et des "setters" dans le cas de l'option var ). Le getter automatique, dans le cas de l'OP, est appelé getContext() mais la classe de base possède déjà un getContext() (même signature).

Le plus probable est que l'intention ici était de simplement faire passer le fichier context au super, dans ce cas, l'autre réponse est la meilleure. Mais, dans le cas où une nouvelle propriété est souhaitée, mais que le nom choisi entre en conflit avec un membre du super ayant un but différent, changer le nom est l'alternative.

En bref le changement de nom s'applique lorsque vous faire veulent une nouvelle variable membre mais une super classe expose déjà un membre différent du même nom.

5voto

Changez le nom de la variable en myContext et vous pourrez travailler avec vous sans problème.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X