用于访问具有不同字段名称的类似对象的设计模式

时间:2014-01-11 16:24:30

标签: java design-patterns polymorphism gson

在这种情况下,哪种设计模式最适合。

public class PersonFromDB1 {
  private String firstName;
  private String lastName;
  private String Car;
}

public class PersonFromDB2 {
  private String first_name;
  private String last_name;
  private String boat;
}

在这两种人类型中,我想要处理的唯一数据是拳头名称和姓氏,无论其字段名称在不同DB中的名称如何。 firstName和first_name表示相同的人员/客户名称 - lastName和last-name也是如此。在我的例子中,汽车和船只领域完全不相关,因此应该被忽略。

使用,也许是多态或适配器模式(?),我想创建一个对象列表,其中包含来自同一类型的DB1和DB2的PersonInOurDB。

最后,我的目标是能够单独在myClass上调用GSON序列化/去除化身。

public class PersonInOurDB {
  private String firstname;
  private String lastname;
}

2 个答案:

答案 0 :(得分:0)

基于类型的简单选择就是您真正需要的。这可以被视为构建器模式,因为它只是初始化myClass的新实例。

注意,这是粗略的伪代码。

FunctionName(SomeType instance)
{
  string aPostfix = "_1";
  string bPostfix = "_2";

  string selectedPostFix;

// This is your strategy selector
  switch(typeof(SomeType.Name)
  {
    case "TypeA":
      selectedPostFix = aPostFix;
    case "TypeB":
      selectedPostFix = bPostFix;
  } 

  return new myClass()
  {
    A = instance.GetProperty("A" + selectedPostfix).Value,
    B = instance.GetProperty("B" + selectedPostfix).Value,
    ...

  }
}

答案 1 :(得分:0)

如果你想在两个对象的java中使用公共访问api,那么引入一个接口并让它们实现它。

如果您只希望json以相同的方式序列化两个对象(PersonFromDB1PersonFromDB2),您可以:

  • 使用注释 - @SerializedName注释与@Expose结合使用。
  • 使用FieldNamingStratgyExclusionStrategy

使用注释来控制序列化

public class PersonFromDB1 {

    @Expose
    @SerializedName("firstName")
    private String firstName;

    @Expose
    @SerializedName("lastName")
    private String lastName;

    private String car;
}

public class PersonFromDB2 {

    @Expose
    @SerializedName("firstName")
    private String first_Name;

    @Expose
    @SerializedName("lastName")
    private String last_Name;

    private String boat;
}

然后您可以使用GsonBuilder

Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation().create();
PersonFromDB1 person1 = ...; // get the object
PersonFromDB2 person2 = ...; // get the object

System.out.println(gson.toJson(person1));
System.out.println(gson.toJson(person2));

使用FieldNamingStratgyExclusionStrategy来控制序列化

如果您不想修改数据库对象(您不能或不想添加注释),则可以使用其他方法。您可以使用FieldNamingStratgyExclusionStrategy

class PersonFromDBNamingStrategy implements FieldNamingStrategy {

    Map<String, String> fieldMapping = new HashMap<String, String>();

    public PersonFromDBNamingStrategy() {
        fieldMapping.put("first_Name", "firstName");
        fieldMapping.put("last_Name", "lastName");
    }

    @Override
    public String translateName(Field f) {
        String name = f.getName();
        if(fieldMapping.contains(name)){
             return fieldMapping.get(name);
        }
        return name;    
    }
}

ExclusionStrategy

class PersonFromDExclusionStrategy implements ExclusionStrategy {

    List<String> validNames = Arrays.asList("car", "boat");

    @Override
    public boolean shouldSkipField(FieldAttributes f) {
        String name = f.getName();
        return !validNames.contains(name);
    }

    @Override
    public boolean shouldSkipClass(Class<?> clazz) {
        return false;
    }
}

之后就像这样创建Gson:

GsonBuilder gsonBuilder = new GsonBuilder();
sonBuilder.addSerializationExclusionStrategy(new PersonFromDExclusionStrategy());
gsonBuilder.setFieldNamingStrategy(new PersonFromDBNamingStrategy());
Gson gson = gsonBuilder.create();

PersonFromDB1 person1 = ...; // get the object
PersonFromDB2 person2 = ...; // get the object

System.out.println(gson.toJson(person1));
System.out.println(gson.toJson(person2));