Kotlin 注解Annotation实践

先做一个简单的联系, 后续的内容逐步补上.

定义Annotion类

@Target(AnnotationTarget.FIELD)
annotation class Car(
    val message: String,
    val title: String
)

其中annotation class上可以用的注解及含义如下

  • @Target, 应用在哪些地方
  • @Retention 该注解是否存在编译好的class文件中, 默认为true. (还没有实践, 可能和注解生效的时间有关系, 注解可以在编译时间生效, 也可以在运行时生效)
  • @Repeatable 是否可以在单个元素上多次使用该注解. 暂时也没有实践
  • @MustBeDocumented 指定该注解是公有 API 的一部分,并且应该包含在生成的 API 文档中显示的类或方法的签名中(还没有实践)

其中, @Target的可以取以下值.

public enum class AnnotationTarget {
    /** Class, interface or object, annotation class is also included */
    CLASS,
    /** Annotation class only */
    ANNOTATION_CLASS,
    /** Generic type parameter (unsupported yet) */
    TYPE_PARAMETER,
    /** Property */
    PROPERTY,
    /** Field, including property's backing field */
    FIELD,
    /** Local variable */
    LOCAL_VARIABLE,
    /** Value parameter of a function or a constructor */
    VALUE_PARAMETER,
    /** Constructor only (primary or secondary) */
    CONSTRUCTOR,
    /** Function (constructors are not included) */
    FUNCTION,
    /** Property getter only */
    PROPERTY_GETTER,
    /** Property setter only */
    PROPERTY_SETTER,
    /** Type usage */
    TYPE,
    /** Any expression */
    EXPRESSION,
    /** File */
    FILE,
    /** Type alias */
    @SinceKotlin("1.1")
    TYPEALIAS
}

当然我们这里暂时只实践一下field. 其他的以后再说

Field注解实践

我们定义一个类, 将注解标注在类成员变量上

class AnnotationActivity : BaseActivity<ActivityAnnotationBinding>() {

    @Car(message = "car message", title = "car title")
    lateinit var machine: Machine
    override fun getLayoutId(): Int {
        return R.layout.activity_annotation
    }

    override fun afterActivityCreate() {
        CarManager.inject(this) //在这里完成machine类的初始化
        binding.content.text = "${machine.myTitle}\n${machine.myContent}"
    }
}

其中Machine类的定义如下

class Machine {
    var myTitle: String? = null
    var myContent: String? = null
}

CarManager的定义如下

object CarManager {
    fun inject(any: Any) {
        val clazz = any::class.java
        val fields = clazz.declaredFields
        for (field in fields) {
            logcat("fieldName:${field.name}")
            logcat("canonicalName:${clazz.canonicalName}")
            logcat("simpleName:${clazz.simpleName}")
            logcat("componentType:${clazz.componentType}")
            if (field.isAnnotationPresent(Car::class.java)) {
                val car = field.getAnnotation(Car::class.java)
                logcat("fieldType:${field.type}")
                logcat("car:$car")
                if (field.type == Machine::class.java) {
                    field.isAccessible = true
                    val machine = Machine().apply {
                        this.myTitle = car!!.title
                        this.myContent = car.message
                    }
                    field.set(any, machine)
                }
            }
        }
    }
}

代码的含义很容易读懂, 不再啰嗦.
如上, 我们就利用注解完成了类成员变量的初始化.

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值