【问题标题】:How to create compile-time constant in Kotlin from enum?如何从枚举在 Kotlin 中创建编译时常量?
【发布时间】:2020-05-06 16:32:30
【问题描述】:

我有一个注释,要求 defaultValue 是编译时常量。我从下面的enum 中取defaultValue

enum class RaceType {
    MARATHON,
    SPRINT;

    companion object {
        fun apply(type: RaceType): RaceDto {
            return when (type) {
                MARATHON -> MarathonDto()
                SPRINT -> SprintDto()
            }
        }
    }
}

我的dtos 如下:

interface RaceDto {
}

data class MarathonDto: RaceDto

data class SprintDto: RaceDto

当我使用注解 @QraphQLArgument(defaultValue = RaceType.SPRINT.name) 时,Kotlin 要求 RaceType.SPRINT.name 是编译时常量。

注解实现本身:

@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.PARAMETER})
public @interface GraphQLArgument {
    String NONE = "\n\t\t\n\t\t\n\ue000\ue001\ue002\n\t\t\t\t\n";
    String NULL = "\n\t\t\n\t\t\n\ue000\ue001\ue002\ue003\n\t\t\t\t\n";

    String name();

    String description() default "";

    String defaultValue() default "\n\t\t\n\t\t\n\ue000\ue001\ue002\n\t\t\t\t\n";

    Class<? extends DefaultValueProvider> defaultValueProvider() default JsonDefaultValueProvider.class;
}

我查看了similar questions,但没有找到解决方法。我还发现了与该主题相关的article,但到目前为止没有任何效果。

旁注:我无法更改注释,因为它来自库,我也无法更改库。

总而言之,有没有办法让 Kotlin 中的 enum 编译时常量在注解中使用?

【问题讨论】:

    标签: kotlin annotations compile-time-constant graphql-spqr


    【解决方案1】:

    有没有办法让 Kotlin 中的 enum 编译时常量在注解中使用?

    不,因为正式的 enums aren't compile-time constants in Java

    但是请考虑sealed 类:

    sealed class RaceType {
        object MARATHON: RaceType() {
            const val name = "MARATHON" // copy-paste is required here until https://youtrack.jetbrains.com/issue/KT-16304
        }
        object SPRINT: RaceType()
    
        companion object {
            fun apply(type: RaceType): RaceDto {
                return when (type) { // the check is in compile time, because of sealed class
                    MARATHON -> MarathonDto()
                    SPRINT -> SprintDto()
                }
            }
        }
    }
    

    仍然需要一小部分复制粘贴。请投票kotlin compiler bugfollow this thread

    但是,据我了解,不幸的是,这并不能解决您对@QraphQLArgument(defaultValue = RaceType.SPRINT.name) 的问题,因为类的名称与值不同。换句话说,对于密封类,您需要编写代码将输入字符串转换为它们。

    【讨论】:

    • 谢谢。这是一个很好的解决方法,至少我知道为什么我找不到解决方案。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-04-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-25
    • 1970-01-01
    • 2020-07-01
    相关资源
    最近更新 更多