返回动态确定的子类对象的方法

时间:2018-03-22 07:47:16

标签: java casting

在CA Automic Automation Engine Java API中,每个AE对象*类型都有自己的UC4Object子类。使用AE对象的许多操作都特定于AE对象类型。我想编写一个以UC4Object作为输入的方法,并返回适合于AE对象类型的类的对象 - 例如,该方法为工作流返回类型为JobPlan的对象。

可以使用UC4Object.getType()确定AE对象类型。一旦知道了AE对象类型,就可以将其UC4Object对象转换为特定于AE对象类型的类。例如,如果正在使用名为uc4Object的UC4Object对象,可能会执行以下操作:

if ("JOBP".equals(uc4Object.getType())){
  JobPlan workflow = (JobPlan) uc4Object;
}

JOBPworkflows的AE对象类型。我想概括一下这样它适用于所有AE对象类型。

UC4Object.getType()    UC4Object Subclass
JSCH                   Schedule
JOBP                   JobPlan
EVNT_TIME              TimeEvent
EVNT_FILE              FileEvent
EVNT_DB                DatabaseEvent
EVNT_CONS              ConsoleEvent
SCRI                   Script
JOBS                   Job
JOBF                   FileTransfer

*通过 AE对象,我的意思是objects in the Automation Engine。这是与Java中的对象不同的概念。

更新1 我可以按如下方式获取要转换的类的名称:

String uc4ObjectClassName = uc4Object.getClass().getSimpleName();
System.out.println(String.format("Object is an instance of class %s.", uc4ObjectClassName));

我希望能有一个简单的回归这个类的对象。

2 个答案:

答案 0 :(得分:1)

  

我想编写一个以UC4Object作为输入的方法,然后返回   适合于AE对象类型的类的对象 - 例如,   method返回工作流的JobPlan类型的对象。

您可以创建一个方法,根据getType()值向下转换对象并返回它。 但是从方法的客户端,您无法直接操作此类型,因为客户端不知道返回的类型。
这意味着您应该在返回之前对cast对象应用处理/工作。

关于实现映射的方式,因为您想要操纵特定的子类型,所以您没有其他选择使用一系列条件语句。

要允许客户端操作特定的子类型,您可能应该首先将所有对象强制转换为其子类型,并将所有对象存储在包含特定类型字段的自定义Workflow结构中。

这可能看起来像:

public class Workflow{
    private List<JobPlan> jobPlans;
    private List<Schedule> schedules;
    ...
}

UC4Object个实例中加载并存储所有Workflow

List<UC4Object> workflowObjects = ...;
Workflow myWorkflow  = new WorkflowMapper().create(workflowObjects);

通过这种方式,客户可以找到所有这些:

List<JobPlan> jobPlans = myWorkflow.getJobPlans();
List<Schedule> schedules = myWorkflow.getSchedules();

或单独(例如id):

int id = 1;
JobPlan jobPlan = myWorkflow.getJobPlan(id);
Schedule schedule = myWorkflow.getSchedule(id);

通过这种方式,您还有另一个优势:在向下转换过程中您不再需要使用一系列条件语句,因为现在唯一的处理是在Workflow实例中添加它们。

您可以在mapper类中存储Map<String, Consumer<UC4Object>>,其中Consumer是工作流的setter方法。

它可以提供一些东西:

public class WorkflowMapper {

    Map<String, Consumer<UC4Object>> map = new HashMap<>();

    private Workflow workflow = new Workflow();

    {
        map.put("JOBP", (uc4Object) -> workflow.setJobPlan((JobPlan) uc4Object));
        map.put("EVNT_TIM", (uc4Object) -> workflow.setTimeEvent((TimeEvent) uc4Object));
        // and so for ...
    }

    public Workflow create(List<UC4Object> uc4Objects) {
        for (UC4Object o : uc4Objects) {

            final String type = o.getType();
            map.getOrDefault(type, (t) -> {
                throw new IllegalArgumentException("no matching for getType = " + t);
            })
               .accept(o);
        }
        return workflow;
    }
}

答案 1 :(得分:0)

我意识到在这种特殊情况下,我可以避免由于该方法能够返回不同类型的对象而引入的复杂性。

\Z的子类都共享一个UC4Object方法,该方法返回类XHeader的对象。 这就是我目前所需要的,因此我可以使header()方法的返回类型。

XHeader

我很高兴知道如何改进这种方法。