使用 @Autowired
|
在包含在本节的示例中,JSR 330 的 |
您可以将 @Autowired 注解应用于构造函数,如下例所示:
-
Java
public class MovieRecommender {
private final CustomerPreferenceDao customerPreferenceDao;
@Autowired
public MovieRecommender(CustomerPreferenceDao customerPreferenceDao) {
this.customerPreferenceDao = customerPreferenceDao;
}
// ...
}
|
如果目标 bean 最初只定义了一个构造函数,则不再需要在此类构造函数上添加 |
您还可以将 @Autowired 注解应用于 传统 的 setter 方法,如下例所示:
-
Java
public class SimpleMovieLister {
private MovieFinder movieFinder;
@Autowired
public void setMovieFinder(MovieFinder movieFinder) {
this.movieFinder = movieFinder;
}
// ...
}
您还可以将注解应用于具有任意名称和多个参数的方法,如下例所示:
-
Java
public class MovieRecommender {
private MovieCatalog movieCatalog;
private CustomerPreferenceDao customerPreferenceDao;
@Autowired
public void prepare(MovieCatalog movieCatalog,
CustomerPreferenceDao customerPreferenceDao) {
this.movieCatalog = movieCatalog;
this.customerPreferenceDao = customerPreferenceDao;
}
// ...
}
您也可以将 @Autowired 应用于字段,甚至可以将其与构造函数混合使用,如下例所示:
-
Java
public class MovieRecommender {
private final CustomerPreferenceDao customerPreferenceDao;
@Autowired
private MovieCatalog movieCatalog;
@Autowired
public MovieRecommender(CustomerPreferenceDao customerPreferenceDao) {
this.customerPreferenceDao = customerPreferenceDao;
}
// ...
}
|
确保您的目标组件(例如, 对于 XML 定义的 bean 或通过类路径扫描找到的组件类,容器通常预先知道具体类型。
但是,对于 |
您还可以通过将 @Autowired 注解添加到期望该类型数组的字段或方法中,指示 Infra 提供 ApplicationContext 中所有特定类型的 bean,如下例所示:
-
Java
public class MovieRecommender {
@Autowired
private MovieCatalog[] movieCatalogs;
// ...
}
这也适用于类型化集合,如下例所示:
-
Java
public class MovieRecommender {
private Set<MovieCatalog> movieCatalogs;
@Autowired
public void setMovieCatalogs(Set<MovieCatalog> movieCatalogs) {
this.movieCatalogs = movieCatalogs;
}
// ...
}
|
如果您希望数组或列表中的项按特定顺序排序,您的目标 bean 可以实现 您可以在目标类级别和 请注意,标准 |
只要预期的键类型为 String,即使是类型化的 Map 实例也可以自动装配。
映射值包含所有预期类型的 bean,键包含相应的 bean 名称,如下例所示:
-
Java
public class MovieRecommender {
private Map<String, MovieCatalog> movieCatalogs;
@Autowired
public void setMovieCatalogs(Map<String, MovieCatalog> movieCatalogs) {
this.movieCatalogs = movieCatalogs;
}
// ...
}
默认情况下,当没有匹配的候选 bean 可用于给定的注入点时,自动装配会失败。 在声明数组、集合或映射的情况下,至少需要一个匹配元素。
默认行为是将带注解的方法和字段视为指示所需的依赖项。
您可以像下面的示例演示的那样更改此行为,通过将其标记为非必需(即,通过将 @Autowired 中的 required 属性设置为 false),使框架能够跳过不可满足的注入点:
-
Java
public class SimpleMovieLister {
private MovieFinder movieFinder;
@Autowired(required = false)
public void setMovieFinder(MovieFinder movieFinder) {
this.movieFinder = movieFinder;
}
// ...
}
|
如果非必需方法的依赖项(或在多个参数的情况下的依赖项之一)不可用,则根本不会调用该方法。 在这种情况下,非必需字段根本不会被填充,从而保留其默认值。 换句话说,将 |
注入的构造函数和工厂方法参数是一个特例,因为 @Autowired 中的 required 属性由于 Infra 构造函数解析算法可能处理多个构造函数而具有稍微不同的含义。
构造函数和工厂方法参数实际上在默认情况下是必需的,但在单构造函数场景中有一些特殊规则,例如如果没有匹配的 bean 可用,多元素注入点(数组、集合、映射)解析为空实例。
这允许一种常见的实现模式,其中所有依赖项都可以在唯一的参数构造函数中声明——例如,声明为没有 @Autowired 注解的单个公共构造函数。
|
任何给定的 bean 类中只有一个构造函数可以将 |
或者,您可以通过 Java 8 的 java.util.Optional 表达特定依赖项的非必需性质,如下例所示:
public class SimpleMovieLister {
@Autowired
public void setMovieFinder(Optional<MovieFinder> movieFinder) {
...
}
}
您还可以使用 @Nullable 注解(任何包中的任何类型——例如,JSR-305 中的 javax.annotation.Nullable)或仅利用 Kotlin 内置的空安全支持:
-
Java
public class SimpleMovieLister {
@Autowired
public void setMovieFinder(@Nullable MovieFinder movieFinder) {
...
}
}
您还可以将 @Autowired 用于众所周知的可解析依赖项接口:BeanFactory、ApplicationContext、Environment、ResourceLoader、ApplicationEventPublisher 和 MessageSource。
这些接口及其扩展接口,如 ConfigurableApplicationContext 或 PatternResourceLoader,会自动解析,无需特殊设置。
以下示例自动装配一个 ApplicationContext 对象:
-
Java
public class MovieRecommender {
@Autowired
private ApplicationContext context;
public MovieRecommender() {
}
// ...
}
|
|