Intereting Posts
Как я могу получить время, необходимое для проверки производительности функций в Котлине Android Studio 3.0 gradle 3.0.0-beta2, ломает Kotlin Unit Test Coverage? onActivityResult не получает вызов при вызове java-активности из kotlin для результата Как переопределить свойства классов java в Котлине? ReactiveStreams NPE при использовании publishOn с пользовательским издателем Поддержка перехода фрагмента 25.1.0 с Recyclerview Kotlin и новый ActivityTestRule: @Rule должен быть общедоступным Котлин назначает делегата после объявления переменной У меня ошибка в студии android с kotlin Создание абстрактного Spek для инициализации общих объектов с помощью Kotlin and Spek Array / List iteration без дополнительных распределений объектов Почему Kotlin для разработчиков Android (книга) нужно снова добавить parseList? Студия андроида Kotlin Я пытаюсь изменить текст кнопки, но получаю сообщение «exepected a value of boolean» Что отличает <reified T> от <reified T: Any> в Котлине? Kotlin смешивается с ошибкой Java: не удается найти символ

Функция расширения Котлина на изменчивом свойстве

Я пытаюсь установить функцию расширения на свойство mutable, чтобы я мог переназначить свойство в функции расширения. Я хотел знать, возможно ли это.

Мои цели – сделать расширения Date для легкого доступа. Например:

 fun Date.addDays(nrOfDays: Int): Date { val cal = Calendar.getInstance() cal.time = this cal.add(Calendar.DAY_OF_YEAR, nrOfDays) return cal.time } 

Эта функция добавляет количество дней к дате, используя объект « Calendar . Проблема заключается в том, что каждый раз я должен возвращать новую дату, которая может сбивать с толку при переназначении каждый раз, когда вы используете эту функцию.

Что я пробовал:

 fun KMutableProperty0<Date>.addDays(nrOfDays: Int) { val cal = Calendar.getInstance() cal.time = this.get() cal.add(Calendar.DAY_OF_YEAR, nrOfDays) this.set(cal.time) } 

К сожалению, это нельзя использовать для объекта Date .

Можно ли сделать это?

К сожалению, вы не можете определить расширение для свойства члена и свободно его использовать в Kotlin 1.0.3.

Ваше расширение можно переписать для работы следующим образом:

 fun <T> KMutableProperty1<T, Date>.addDays(receiver: T, nrOfDays: Int) { val cal = Calendar.getInstance() cal.time = this.get(receiver) cal.add(Calendar.DAY_OF_YEAR, nrOfDays) this.set(receiver, cal.time) } 

со следующим использованием:

 class C(var date: Date) { ... } val c = C(someDate()) C::date.addDays(c, 123) 

С привязанными вызываемыми ссылками (вероятно, поддерживается в Kotlin 1.1) это будет возможно со следующим синтаксисом:

 c::date.addDays(123) 

Как предлагает @ MarcinKoziński, вы также можете мутировать объекты Date без переопределения свойства:

 fun Date.addDays(nrOfDays: Int) { val cal = Calendar.getInstance() cal.time = this cal.add(Calendar.DAY_OF_YEAR, nrOfDays) this.time = cal.timeInMillis } 

с использованием:

 class C(var date: Date) val c = C(someDate()) c.date.addDays(123) 

С помощью этого решения вы должны контролировать ссылки на объект Date который мутирован. Это решение хорошо работает с изменяемыми объектами, хотя оно не подходит для хранения неизменяемых объектов.

Вместо того, чтобы возвращать новую Date и пытаться обновить ваше свойство, вы можете просто изменить Date которую уже имеет ваша собственность:

 fun Date.addDays(nrOfDays: Int) { val cal = Calendar.getInstance() cal.time = this cal.add(Calendar.DAY_OF_YEAR, nrOfDays) this.time = cal.timeInMillis }