【发布时间】:2012-05-03 10:31:24
【问题描述】:
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() - 不使用几乎强制设计的构造函数。我在想一个工厂,但是在一个更大的项目中为每个班级都建一个工厂似乎不是一个好主意。
类似:
<bean ... factory-method="..." depends-on="..." lazy-init="..."/>
并在工厂方法中实例化类并调用方法createList()。 或者像这样从某个方法调用它 - 这又看起来很糟糕,迫使该方法有责任实例化对象图。
我想在运行时解决的运行时依赖的图片如下:
是否有其他方法可以根据用户交互使用容器来实现动态延迟初始化?
谢谢。
【问题讨论】:
-
我不知道你在问什么。 “解决方法调用 createList() 或 createSecondList()”是什么意思?如果我对您尝试做的事情的猜测是正确的(我对此表示怀疑),我将创建一个工厂类,该类具有(静态?)工厂方法,该方法采用交互式参数并创建适当的列表,然后注入将该类的工厂对象放入您的 Main 对象中。
-
我以为你会从上下文中理解。不是一个伟大的问题作家。是的,像这样。问题加粗了。除了工厂(当然是静态的)和使用对象的拉取/初始化(在主类中进行初始化,“main”方法)之外,我如何构造动态对象图,这样我就不必担心架构“代码“在我的申请中。为什么要在 Main 对象中注入工厂对象?如果你所有的课程都是动态的,你会有很多工作。因为您应该在每个动态类上都有一个工厂。我仍然相信有一个更简单的解决方案:)
标签: java spring dependency-injection factory factory-pattern