获取相似对象属性的通用方法
Generalized method to get similar object attributes
我有一个对象,它有几个数组作为字段。 class 大致是这样的:
public class Helper {
InsuranceInvoices[] insuranceInvoices;
InsuranceCollectiveInvoices[] insuranceCollectiveInvoices
BankInvoices[] bankInvoices;
BankCollectiveInvoices[] bankCollectiveInvoices;
}
所有发票类型都有一个共同的标记界面发票。
我需要获取所有发票才能对其调用另一种方法。
Helper helperObject = new Helper();
// ...
for (InsuranceInvoices invoice : helperObject.getInsuranceInvoices()) {
Integer customerId = invoice.getCustomerId();
// ...
}
for (BankInvoices invoice : helperObject.getBankInvoices()) {
Integer customerId = invoice.getCustomerId();
// ...
}
// repeat with all array fields
问题是所有的发票只有标记界面是共同的。方法 getCustomerID() 不是由相互接口或 class 定义的。由于给定的规范,这是我无法更改的行为。
for-each-loop 中的代码重复让我很烦恼。我必须对四个不同数组中的所有发票对象执行完全相同的操作。因此,四个 for-each-loops 不必要地使代码膨胀。
有没有办法可以编写通用(私有)方法?一个想法是:
private void generalMethod(Invoice[] invoiceArray){
// ...
}
但这需要四次 instanceof 检查,因为 class Invoice 不知道方法 getCusomterId()。因此,我将一无所获;该方法仍将包含重复。
我感谢所有可能的解决方案来概括这个问题!
它不漂亮,但是您可以使用反射来查找getCustomerId
Method and then invoke() it, cf. Class.getDeclaredMethod()。
private void generalMethod(Invoice[] invoiceArray){
try {
for (Invoice invoice : invoiceArray) {
Method getCustomerId = invoice.getClass().getDeclaredMethod("getCustomerId");
getCustomerId.invoke(invoice);
}
} catch (Exception e) {
// ...
}
}
请注意这是未经测试的。
如果不允许您通过向它们添加自定义界面来更改您正在处理的 classes。您可以做的最好的事情是用具有所需属性的自定义 class 包装它们。
通过这种方式,您将拥有一个 class,其中包含所有 'not so nice' 代码,可将您无法触及的 classes 转换为与适当且匹配的漂亮 classes有用的设计。
例如,您可以有一个扩展 WrappedInsurace
并包含成员字段 InsuranceInvoice
的 class WrappedInsuranceInvoice
。如果您不需要保留原始 class ,那么复制数据会更好。这样您就可以例如丢失数组并改用列表。
概括问题的可能解决方案(从最好到最差排序):
使用包装器class
public class InvoiceWrapper {
private String customerID;
public String getCustomerID() {
return customerID;
}
public InvoiceWrapper(BankInvoices invoice) {
this.customerID = invoice.getCustomerID();
}
public InvoiceWrapper(InsuranceInvoices invoice) {
this.customerID = invoice.getCustomerID();
}
// other constructors
}
Upd 如果我理解正确的话,你需要对所有数组中的 ID 做一些事情。要使用 InvoiceWrapper,您还需要在 Helper class 中实现迭代器,它将遍历数组和 return 每个条目的包装器。因此,无论如何,您将拥有适用于 4 个数组的代码。
使用转换实例
public class CustomerIdHelper {
public static String getID(Invoice invoice) {
if (invoice instanceof InsuranceInvoices) {
return ((InsuranceInvoices) invoices).getCustomerID();
} else if ...
}
}
通过反射按名称调用方法
public class CustomerIdHelper {
public static String getID(Invoice invoice) {
Method method = invoice.getClass().getDeclaredMethod("getCustomerId");
return (String) method.invoke(invoice);
}
}
我有一个对象,它有几个数组作为字段。 class 大致是这样的:
public class Helper {
InsuranceInvoices[] insuranceInvoices;
InsuranceCollectiveInvoices[] insuranceCollectiveInvoices
BankInvoices[] bankInvoices;
BankCollectiveInvoices[] bankCollectiveInvoices;
}
所有发票类型都有一个共同的标记界面发票。
我需要获取所有发票才能对其调用另一种方法。
Helper helperObject = new Helper();
// ...
for (InsuranceInvoices invoice : helperObject.getInsuranceInvoices()) {
Integer customerId = invoice.getCustomerId();
// ...
}
for (BankInvoices invoice : helperObject.getBankInvoices()) {
Integer customerId = invoice.getCustomerId();
// ...
}
// repeat with all array fields
问题是所有的发票只有标记界面是共同的。方法 getCustomerID() 不是由相互接口或 class 定义的。由于给定的规范,这是我无法更改的行为。
for-each-loop 中的代码重复让我很烦恼。我必须对四个不同数组中的所有发票对象执行完全相同的操作。因此,四个 for-each-loops 不必要地使代码膨胀。
有没有办法可以编写通用(私有)方法?一个想法是:
private void generalMethod(Invoice[] invoiceArray){
// ...
}
但这需要四次 instanceof 检查,因为 class Invoice 不知道方法 getCusomterId()。因此,我将一无所获;该方法仍将包含重复。
我感谢所有可能的解决方案来概括这个问题!
它不漂亮,但是您可以使用反射来查找getCustomerId
Method and then invoke() it, cf. Class.getDeclaredMethod()。
private void generalMethod(Invoice[] invoiceArray){
try {
for (Invoice invoice : invoiceArray) {
Method getCustomerId = invoice.getClass().getDeclaredMethod("getCustomerId");
getCustomerId.invoke(invoice);
}
} catch (Exception e) {
// ...
}
}
请注意这是未经测试的。
如果不允许您通过向它们添加自定义界面来更改您正在处理的 classes。您可以做的最好的事情是用具有所需属性的自定义 class 包装它们。
通过这种方式,您将拥有一个 class,其中包含所有 'not so nice' 代码,可将您无法触及的 classes 转换为与适当且匹配的漂亮 classes有用的设计。
例如,您可以有一个扩展 WrappedInsurace
并包含成员字段 InsuranceInvoice
的 class WrappedInsuranceInvoice
。如果您不需要保留原始 class ,那么复制数据会更好。这样您就可以例如丢失数组并改用列表。
概括问题的可能解决方案(从最好到最差排序):
使用包装器class
public class InvoiceWrapper {
private String customerID;
public String getCustomerID() {
return customerID;
}
public InvoiceWrapper(BankInvoices invoice) {
this.customerID = invoice.getCustomerID();
}
public InvoiceWrapper(InsuranceInvoices invoice) {
this.customerID = invoice.getCustomerID();
}
// other constructors
}
Upd 如果我理解正确的话,你需要对所有数组中的 ID 做一些事情。要使用 InvoiceWrapper,您还需要在 Helper class 中实现迭代器,它将遍历数组和 return 每个条目的包装器。因此,无论如何,您将拥有适用于 4 个数组的代码。
使用转换实例
public class CustomerIdHelper {
public static String getID(Invoice invoice) {
if (invoice instanceof InsuranceInvoices) {
return ((InsuranceInvoices) invoices).getCustomerID();
} else if ...
}
}
通过反射按名称调用方法
public class CustomerIdHelper {
public static String getID(Invoice invoice) {
Method method = invoice.getClass().getDeclaredMethod("getCustomerId");
return (String) method.invoke(invoice);
}
}