Комната не может выбрать конструктор, поскольку подходящие ошибки являются множественными конструкторами

Я пытаюсь реализовать постоянную библиотеку в моем проекте android kotlin, но поймаю эту ошибку во время компиляции:

error: Room не может выбрать конструктор, поскольку подходят несколько конструкторов. Попробуйте аннотировать нежелательные конструкторы с помощью @Ignore.

Код ошибки:

@Entity data class Site( var name: String = "", var url: String = "", @PrimaryKey(autoGenerate = true) var id: Long = 0) 

У меня была эта ошибка, потому что Котлин, по-видимому, генерирует несколько конструкторов Java для одного конструктора Kotlin со значениями аргументов по умолчанию. Рабочий код см. Ниже:

 @Entity data class Site( var name: String, var url: String, @PrimaryKey(autoGenerate = true) var id: Long) 

Это сработало для меня:

 @Entity data class Site( @PrimaryKey(autoGenerate = true) var id: Long = 0), var name: String = "", var url: String = "", @Ignore var ignored: String? = null ) 

Ни одно из вышеперечисленных решений не является хорошим, поскольку они работают, но могут вызывать ошибки.

Класс данных Kotlin генерирует несколько методов с использованием конструктора по умолчанию. Это означает, что функции equals () , hashCode () , toString () , componentN () и copy () генерируются с использованием атрибутов, назначаемых вашему конструктору.

Используя вышеупомянутые решения, такие как

 @Entity data class Site(@PrimaryKey(autoGenerate = true) var id: Long) { @Ignore constructor() : this(0) var name: String = "" var url: String = "" } 

генерирует все перечисленные выше методы только для id. Использование equals приводит к нежелательному качеству, так же как toString (). Для этого необходимо, чтобы у вас были все атрибуты, которые вы хотите обработать внутри конструктора, и добавьте второй конструктор, используя ignore like

 @Entity data class Site( @NonNull @PrimaryKey(autoGenerate = true) var id: Long, var name: String = "", var url: String = "") { @Ignore constructor(id = 0, name = ", url = "") : this() } 

Вы действительно должны иметь в виду, что вы обычно используете классы данных, чтобы иметь такие методы, как toString и копировать. Только это решение работает во избежание нежелательных ошибок во время выполнения.

Здесь вы меняете version своего приложения и перезапускаете программу agian, она будет работать:

 @Database(entities = arrayOf(Site::class), version = 123) abstract class YourAppDatabase : RoomDatabase() { abstract fun yourDao(): YourDao } 

и вы также можете попробовать этот data class :

  @Entity data class Site(@PrimaryKey(autoGenerate = true) var id: Long) { @Ignore constructor() : this(0) var name: String = "", var url: String = "", } 

и последней инструкции: ваш первичный ключ должен быть увеличен вручную .

Надеюсь, это сработает для вас. 🙂

Проверьте, что приведенные выше ответы неверны.

 data class TestModel(var id: Int = 0) { constructor() : this(0) var name: String = "defaultname" var testData: String = "defaulttestData" } val testModel = TestModel(5) testModel.name = "test" val testModel2 = TestModel(5) testModel2.testData = "testdata" testModel2.name = "test" info { "Test with name set: $testModel" } info { "Testdata equals Testdata2 ${testModel.equals(testModel2)}" } 

возвращает Test с набором имен: TestModel (id = 5) и Testdata равно Testdata2 true