标签: kotlin-delegate

Kotlin:引用未由构造函数传递的委托

我想在特定的上下文中使用Kotlin 委托。

  • 不应在构造函数中传递委托。
  • 我想保留对委托的引用以供以后在代码中使用。例如,在我重写的方法中printMessage(),我仍然需要以与多态继承中调用的方式相同的方式调用委托super.printMessage()

我可以通过简单地在子句中实例化匿名委托来完成第一个任务byclass Derived() : Base by BaseImpl(42)使用Kotlin 的文档示例)。但是,这阻止了我访问匿名委托,因为我不知道如何引用它。

我想做类似以下的事情。然而,以下内容编译时不会出现错误'this' is not defined in this context

class Derived() : Base by this.b {
    
    val b: Base = BaseImpl(42)
    
    override fun printMessage() {
        b.printMessage()
        print("abc")
    }
}
Run Code Online (Sandbox Code Playgroud)

我确实需要为班级的每个实例分配一个单独的委托Derived。因此,作为全局变量移动b对我来说不是一个选择。

我最接近我需要的是构造函数的可选参数。这也不是一个好的选择,因为我不想允许Derived用任意的代表构建我的类。

delegates delegation kotlin kotlin-delegate

6
推荐指数
1
解决办法
946
查看次数

如何结合 kotlin 委托属性:可观察、可否决和“按地图”?

我正在尝试将delegates/observablevetoable结合起来(在查看源 kotlin.properties.Delegates.kt 后这不是问题),但是在尝试将属性存储在 map 中时事情变得棘手。

或者换句话说,如何将这三者结合起来:

var k1: Int by Delegates.observable(0) { property, oldValue, newValue ->
    println("Hi from k1 observer")
}

var k2:Int by Delegates.vetoable(0) {property, oldValue, newValue ->
    println("Hi from k2 more-than check")
     oldValue > newValue
}

val myMap = mutableMapOf<String, Int>()
var k3 by myMap
Run Code Online (Sandbox Code Playgroud)

delegates kotlin kotlin-delegate

5
推荐指数
1
解决办法
1160
查看次数

Kotlin 委托属性导致 Android Studio 中的预览渲染错误

我创建了一个自定义属性,专门用于保存需要为我的一个项目调用 invalidate() 的视图属性:

class InvalidatingProperty<T>(private var _value: T) {

    operator fun getValue(thisRef: View, property: KProperty<*>): T {
        return _value
    }

    operator fun setValue(thisRef: View, property: KProperty<*>, value: T) {
        _value = value
        thisRef.invalidate()
    }
}
Run Code Online (Sandbox Code Playgroud)

在另一个项目中,我想重用我以前的一些工作,所以我将视图及其依赖项(包括 InvalidatingProperty)复制到一个新项目中。但在新项目中,使用 InvalidatingProperty 会导致预览渲染失败,并出现以下异常:

java.lang.NoSuchMethodError: kotlin.jvm.internal.MutablePropertyReference1Impl.<init>(Ljava/lang/Class;Ljava/lang/String;Ljava/lang/String;I)V
    at com.gradesimulator.views.SummaryView.<clinit>(SummaryView.kt)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
    at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
    at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
    at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
    at org.jetbrains.android.uipreview.ViewLoader.createNewInstance(ViewLoader.java:403)
    at org.jetbrains.android.uipreview.ViewLoader.loadClass(ViewLoader.java:186)
    at org.jetbrains.android.uipreview.ViewLoader.loadView(ViewLoader.java:144)
    at com.android.tools.idea.rendering.LayoutlibCallbackImpl.loadView(LayoutlibCallbackImpl.java:309)
    at android.view.BridgeInflater.loadCustomView(BridgeInflater.java:416)
    at android.view.BridgeInflater.loadCustomView(BridgeInflater.java:427)
    at android.view.BridgeInflater.createViewFromTag(BridgeInflater.java:331)
    at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:961)
    at android.view.LayoutInflater.rInflate_Original(LayoutInflater.java:1123)
    at android.view.LayoutInflater_Delegate.rInflate(LayoutInflater_Delegate.java:72)
    at android.view.LayoutInflater.rInflate(LayoutInflater.java:1097)
    at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:1084)
    at android.view.LayoutInflater.inflate(LayoutInflater.java:682)
    at android.view.LayoutInflater.inflate(LayoutInflater.java:501) …
Run Code Online (Sandbox Code Playgroud)

android gradle kotlin android-studio kotlin-delegate

5
推荐指数
1
解决办法
706
查看次数

(反)使用 jackson 序列化 kotlin 委托属性

我如何使用 jackson(反)序列化 kotlin 委托属性。我有一堂这样的课

class MyClass {
    var a: Int = 42
        set(value) {
            val changed = field != value
            field = value
            if (changed) notifyListeners()
        }

    ... and a dozen other properties that all follow this pattern ...
}
Run Code Online (Sandbox Code Playgroud)

我想通过使用来简化它

class MyClass {
    var a: Int by NotifyUiOnChange(42)

    ...

    private inner class NotifyUiOnChange<T>(initialValue: T) : ObservableProperty<T>(initialValue) {
        override fun afterChange(property: KProperty<*>, oldValue: T, newValue: T) {
            notifyUiListeners()
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

但随后杰克逊将忽略该属性。
无论如何,我如何告诉杰克逊序列化和反序列化该属性?然后我如何应用 @JsonIgnore 注释(或类似的东西)?

json jackson kotlin kotlin-delegate

2
推荐指数
1
解决办法
1200
查看次数

从重写中使用类委派时调用(基本)委派函数

当覆盖由类委托实现的接口方法时,是否可以从覆盖函数中调用通常委托给该类的类?类似于super使用继承时的调用方式。

文档中

interface Base {
    fun print()
}

class BaseImpl(val x: Int) : Base {
    override fun print() { print(x) }
}

class Derived(b: Base) : Base by b

fun main(args: Array<String>) {
    val b = BaseImpl(10)
    Derived(b).print() // prints 10
}
Run Code Online (Sandbox Code Playgroud)

请注意,重写将按您期望的那样工作:编译器将使用重写实现,而不是委托对象中的实现。

override fun print() { ... }
Run Code Online (Sandbox Code Playgroud)

如何BaseImpl print()从此重写函数中调用该函数?

用例是我想在重用现有实现的同时向此功能添加其他逻辑。

kotlin kotlin-delegate

1
推荐指数
2
解决办法
1165
查看次数