gpt4 book ai didi

java - Spring动态注入(inject),类工厂模式

转载 作者:IT老高 更新时间:2023-10-28 13:53:58 25 4
gpt4 key购买 nike

Dependency injection, delayed injection praxis 的延续.我有主课:

package test;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.stereotype.Component;

import java.util.List;
import java.util.Scanner;

@Component
public class Main {
@Autowired
private StringValidator stringValidator;

@Autowired
private StringService stringService;

@Autowired
private ValidationService validationService;

public void main() {
scanKeyboardCreateLists();

stringValidator.validate();

final List<String> validatedList = stringValidator.getValidatedList();
for (String currentValid : validatedList) {
System.out.println(currentValid);
}
}

private void scanKeyboardCreateLists() {
//Let's presume the user interacts with the GUI, dynamically changing the object graph...
//Needless to say, this is past container initialization...
Scanner scanner = new Scanner(System.in);
int choice = scanner.nextInt();

//Delayed creation, dynamic
if (choice == 0) {
stringService.createList();
validationService.createList();
} else {
stringService.createSecondList();
validationService.createSecondList();
}
}

public static void main(String[] args) {
ApplicationContext container = new ClassPathXmlApplicationContext("/META-INF/spring/applicationContext.xml");
container.getBean(Main.class).main();
}
}

并且对象图是动态创建的,取决于用户交互。我解决了应用程序耦合,让我可以非常简单地测试它。 此外,由于列表由容器维护,因此该应用程序(以及其他所有应用程序)的动态特性是无关紧要的,因为可以在应用程序需要它们的任何时候请求它们,并维护它们的元素。

剩下的代码在这里:

package test;

import java.util.List;

public interface Stringable {
List<String> getStringList();
}

package test;

import org.springframework.stereotype.Component;

import java.util.ArrayList;

@Component
public class StringList extends ArrayList<String> {
}

package test;

import org.springframework.stereotype.Component;

import javax.inject.Inject;
import java.util.ArrayList;
import java.util.List;

@Component
public class StringService implements Stringable {

private List<String> stringList;

@Inject
public StringService(final ArrayList<String> stringList) {
this.stringList = stringList;
}

//Simplified
public void createList() {
stringList.add("FILE1.txt");
stringList.add("FILE1.dat");
stringList.add("FILE1.pdf");
stringList.add("FILE1.rdf");
}

public void createSecondList() {
stringList.add("FILE2.txt");
stringList.add("FILE2.dat");
stringList.add("FILE3.pdf");
stringList.add("FILE3.rdf");
}

@Override
public List<String> getStringList() {
return stringList;
}
}

package test;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.List;

@Component
public class StringValidator {
private List<String> stringList;
private List<String> validationList;

private final List<String> validatedList = new ArrayList<String>();

@Autowired
public StringValidator(final ArrayList<String> stringList,
final ArrayList<String> validationList) {
this.stringList = stringList;
this.validationList = validationList;
}

public void validate() {
for (String currentString : stringList) {
for (String currentValidation : validationList) {
if (currentString.equalsIgnoreCase(currentValidation)) {
validatedList.add(currentString);
}
}
}
}

public List<String> getValidatedList() {
return validatedList;
}
}

package test;

import java.util.List;

public interface Validateable {
List<String> getValidationList();
}

package test;

import org.springframework.stereotype.Component;

import java.util.ArrayList;

@Component
public class ValidationList extends ArrayList<String> {
}

package test;

import org.springframework.stereotype.Component;

import javax.inject.Inject;
import java.util.ArrayList;
import java.util.List;

@Component
public class ValidationService implements Validateable {

private List<String> validationList;

@Inject
public ValidationService(final ArrayList<String> validationList) {
this.validationList = validationList;
}

//Simplified...
public void createList() {
validationList.add("FILE1.txt");
validationList.add("FILE2.txt");
validationList.add("FILE3.txt");
validationList.add("FILE4.txt");
}

public void createSecondList() {
validationList.add("FILE5.txt");
validationList.add("FILE6.txt");
validationList.add("FILE7.txt");
validationList.add("FILE8.txt");
}

@Override
public List<String> getValidationList() {
return validationList;
}
}

有谁知道我将如何解决方法调用 createList() 或 createSecondList() - 不使用几乎强制设计的构造函数。我在考虑建一个工厂,但是在一个更大的项目中为每个类(class)都建一个工厂似乎不是一个好主意。

类似:

<bean ... factory-method="..." depends-on="..." lazy-init="..."/>

并在工厂方法中实例化类并调用方法createList()。或者像这样从某个方法调用它 - 这又看起来很糟糕,迫使该方法有责任实例化对象图。

我想在运行时解决的运行时依赖的图片如下:

enter image description here

是否有其他方法可以根据用户交互使用容器来实现动态延迟初始化?

谢谢。

最佳答案

如果您希望类的某些成员在每次调用相应的 getter 时动态初始化\填充,您可以尝试查找方法注入(inject)。阅读页。 3.3.4.1 here .

所以即使包含动态成员的类是在 scope=singletone 中创建的(spring bean 容器的默认设置)每次访问分配了lookup 方法的字段时,都会根据lookup 方法内部实现的业务逻辑得到一个合适的对象。在您的情况下,列表是一个接口(interface),因此您可以轻松地在查找方法中实现验证并返回经过验证的列表。

编辑:

我找到了更好的 example在 Spring 文档中 - 我认为这很清楚。看看《3.4.6.1 Lookup方法注入(inject)》

当您配置 Main类为其List分配一个查找方法member - 只要您需要 List 的新实例,就会调用它。 bean 。

祝你好运!

关于java - Spring动态注入(inject),类工厂模式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10429572/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com