@AutoAnnotation的作用是什么?如何使用?

问题描述 投票:0回答:1

https://dagger.dev/multibindings.html中,我读到了@AutoAnnotation。它引用了https://github.com/google/auto/blob/master/value/src/main/java/com/google/auto/value/AutoAnnotation.java

https://github.com/google/auto/blob/57dfad360306619a820e6aae4a14a1aa67c29299/value/userguide/howto.md#annotation

我读到它,无法理解。

我设法使用我的Android代码访问它

implementation 'com.google.auto.value:auto-value:1.5.2'
kapt 'com.google.auto.value:auto-value:1.5.2'

还有

android.defaultConfig.javaCompileOptions.annotationProcessorOptions.includeCompileClasspath = true

但是我不知道如何使用。有使用它的任何好的教程吗?

java android annotations dagger-2
1个回答
1
投票

[AutoAnnotation自动生成一个类,该类以与JDK相同的方式实现注释接口。

匕首地图键

[通过使用自定义注释作为其键的Dagger使用Multibindings映射时,Dagger会使用注释实例本身作为键,将实例T或提供者Provider<T>安装到返回的映射中。为了更清楚一点:

@MapKey
@interface YourAnnotation {
  String foo();
}

@Provides @YourAnnotation(foo="bar") YourClass getYourClassForBar() { /* ... */ }

// Dagger will create a multibinding that would allow you to inject this:
@Inject Map<YourAnnotation, YourClass> map;

[如果这里唯一重要的是foo,则也可以使用unwrapKeys使字符串以String而不是YourAnnotation作为键,但是假设您想要这样做,是因为您希望YourAnnotation将来具有多个值。但是YourAnnotation的实现是从哪里来的,应该如何在地图上调用get

运行时注释

当注释Java元素(通常是类,方法或字段)时,Java将返回该类的注释的特定实现。从Java tutorial

@interface ClassPreamble {
   String author();
   String date();
   int currentRevision() default 1;
   String lastModified() default "N/A";
   String lastModifiedBy() default "N/A";
   // Note use of array
   String[] reviewers();
}

// [...]

@ClassPreamble (
   author = "John Doe",
   date = "3/17/2002",
   currentRevision = 6,
   lastModified = "4/12/2004",
   lastModifiedBy = "Jane Doe",
   // Note array notation
   reviewers = {"Alice", "Bob", "Cindy"}
)
public class Generation3List extends Generation2List {/* ... */}

在这种用法中,Generation3List具有一个ClassPreamble类型的注释。如果注释是在运行时保留的(即ClassPreamble本身是annotated with @Retention(RUNTIME)),则可以通过@Retention(RUNTIME)Generation3List.class.getAnnotations()进行访问。 (也有declared对等物以不同方式处理超类注释。)

一旦到达ClassPreamble的实例,就可以使用Generation3List.class.getAnnotations()Generation3List.class.getAnnotation(ClassPreamble.class)之类的方法从类中检索数据。但是,ClassPreamble充当接口,并且该注释的实现在VM内部。这使得在运行时创建您自己的ClassPreamble任意实例变得更加困难。

符合注释的实现

因为YourAnnotation和ClassPreamble是接口,所以您可以只创建一个实现。但是,与VM的实现相比,该实现不太可能具有匹配的Generation3List.class.getAnnotation(ClassPreamble.class)author()实现,因为在JRE之间实现可能有所不同,在Android中也可能有所不同。但是,实际上非常严格地规定了date()equals的实现:

注释的哈希码是其成员(包括具有默认值的哈希值)的哈希码的总和,如下所示:注释成员的哈希码为(成员名称的哈希码的127倍为[...]

由String.hashCode())计算得出成员值的哈希码。

如果指定的对象表示在逻辑上等效于该注释的注释,则返回true。换句话说,如果指定对象是与此实例具有相同注释类型的实例,并且其所有成员都与此注释的对应成员相同,则返回true,如下所示[...

可以手动实施这些规则,但是这样做很难,并且如果要更改YourAnnotation或ClassPreamble的结构,也将带来负担。通过hashCode,自动注释会自动为符合条件的实现生成代码:

equals

[使用AutoAnnotation的生成实现,您可以在Dagger Multibindings生成的地图上调用hashCode(或提供您控制的测试实现),而不必处理特定于批注的in the docs for Annotation XOR或there are reflective solutions to this problem规则。这在Dagger和测试之外非常有用,但是由于Dagger在其映射中使用了注释实例,因此您可能需要使用AutoAnnotation来创建类似实例是有意义的。

© www.soinside.com 2019 - 2024. All rights reserved.