【问题标题】:Kotlin: How can I use delegated properties in Java?Kotlin:如何在 Java 中使用委托属性?
【发布时间】:2017-12-22 15:29:56
【问题描述】:

我知道您不能在 Java 中使用委托属性语法,也无法像在 Kotlin 中那样“覆盖”set/get 运算符,但我仍然想使用现有的属性委托在 Java 中。

例如,一个简单的 int 委托:

class IntDelegate {
    operator fun getValue(thisRef: Any?, property: KProperty<*>) = 0
}

在 Kotlin 中我们当然可以这样使用:

val x by IntDelegate()

但是我们如何在 Java 中以某种形式使用IntDelegate?这是开始,我相信:

final IntDelegate x = new IntDelegate();

然后直接使用函数。但是如何使用getValue 函数呢?我为它的参数传递什么?如何为 Java 字段获取 KProperty

【问题讨论】:

  • 为什么需要调用这样的功能?它仅由 kotlin 可见和使用。

标签: java delegates kotlin delegation delegated-properties


【解决方案1】:

如果你真的想知道 Kotlin 委托属性在 Java 中的外观,这里是:在此示例中,Java 类 JavaClass 的属性 x 被委托给 Delegates.notNull 标准委托。

// delegation implementation details
import kotlin.jvm.JvmClassMappingKt;
import kotlin.jvm.internal.MutablePropertyReference1Impl;
import kotlin.jvm.internal.Reflection;
import kotlin.reflect.KProperty1;

// notNull property delegate from stdlib
import kotlin.properties.Delegates;
import kotlin.properties.ReadWriteProperty;


class JavaClass {
    private final ReadWriteProperty<Object, String> x_delegate = Delegates.INSTANCE.notNull();
    private final static KProperty1 x_property = Reflection.mutableProperty1(
            new MutablePropertyReference1Impl(
                JvmClassMappingKt.getKotlinClass(JavaClass.class), "x", "<no_signature>"));

    public String getX() {
        return x_delegate.getValue(this, x_property);
    }

    public void setX(String value) {
        x_delegate.setValue(this, x_property, value);
    }
}

class Usage {
    public static void main(String[] args) {
        JavaClass instance = new JavaClass();
        instance.setX("new value");
        System.out.println(instance.getX());
    }
}

但我不建议使用此解决方案,不仅因为需要样板文件,还因为它严重依赖委托属性和 kotlin 反射的实现细节。

【讨论】:

    【解决方案2】:

    我知道您不能在 Java 中使用委托属性语法,也无法像在 Kotlin 中那样“覆盖”set/get 运算符,但我仍然想使用现有的属性委托在 Java 中。

    不,就像你在开始时所说的那样,它在 Java 中不存在。但如果你坚持这样做,你可以做类似的事情。

    public interface Delegate<T> {
        T get();
        void set(T value);
    }
    
    public class IntDelegate implements Delegate<Integer> {
        private Integer value = null;
    
        @Override
        public void set(Integer value) {
            this.value = value;
        }
    
        @Override
        public Integer get() {
            return value;
        }
    }
    
    final Delegate<Integer> x = new IntDelegate();
    

    Delcare x in interface 允许你有不同的实现。

    【讨论】:

      猜你喜欢
      • 2015-09-02
      • 2017-07-14
      • 1970-01-01
      • 1970-01-01
      • 2020-05-24
      • 2021-10-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多