首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何使用泛型或函数类避免代码中的重复

问如何使用泛型或函数类避免代码中的重复
EN

Stack Overflow用户
提问于 2022-07-03 15:41:44
回答 1查看 77关注 0票数 2
代码语言:javascript
复制
private <Y> void meth(
            MyObj ds, MultiValueMap<String, List> mvm, Class<Y> data) {

            

        if(data.isAssignableFrom(Employee.class)) {
            for (Employee rd : (List<Employee>) mvm.get(0).get(1)) {
               
                for (String cName : (List<String>) mvm.get(0).get(0)) {
                    ds.setCellValue((String)rd.getDataElement(cName));
                   
                }
               
            }
        }

        if(data.isAssignableFrom(Department.class)) {
            for (Department rd : (List<Department>) mvm.get(0).get(1)) {
               
                for (String cName : (List<String>) mvm.get(0).get(0)) {
                    ds.setCellValue((String)rd.getDataElement(cName));
                    
                }
               
            }
        }
        
        
        //some more similar if conditions as above
        
}

在上面,我有类似的10个如果条件,如何避免重复代码在上面?我是否需要使用任何Java 8函数类作为参数,以避免重复代码(或)必须使用任何额外的泛型代码?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-07-03 16:36:14

虽然可以应用通用方法,但它们不会解决您试图解决的实际场景(在我更深入地考虑这个问题之前,对这个答案的早期编辑是一次尝试)。

退一步看,这看起来像问题陈述(“您要解决的是什么”,而不是“如何解决”):

迭代地图中的所有列表-在发布的代码中,这将是:MultiValueMap<String, List> mvm

  • Accomodate不同的对象类型-您将员工和部门发布为examples

  • Whatever列表包含的列表(员工、部门等),您要调用getDataElement()

正如Ausgefuchster所描述的另一个答案,这可以通过接口来解决。我投票赞成这个答案,但想提供更多的细节和例子。

步骤1:定义接口

不管具体的类是什么,您的映射都包含有getDataElement()的东西列表,所以创建一个接口来捕获它:

代码语言:javascript
复制
interface HasDataElement {
    String getDataElement();
}

步骤2:类实现接口

对于这个答案,我组成了几个简单的类-- A、B和C--它们实现了接口,但在调用getDataElement()时才返回字符串。在您的代码中,您将修改员工、部门等以实现新的接口。

代码语言:javascript
复制
class A implements HasDataElement {
    @Override
    public String getDataElement() {
        return "A";
    }
}

class B implements HasDataElement {
    @Override
    public String getDataElement() {
        return "B";
    }
}

class C implements HasDataElement {
    @Override
    public String getDataElement() {
        return "C";
    }
}

第三步:处理地图

我使用内置类型,所以Map<String, List>而不是使用MultiValueMap<String, List>的发布代码。我认为这种差异并不显著,但无论如何都要指出这一点。

下面的方法签名指定映射不仅仅是<String, List>,而是进一步指定列表本身必须包含扩展HasDataElement接口的内容:List<? extends HasDataElement>。

在该方法中,第一个循环中会显示相同的List<? extends HasDataElement>类型。

一旦进入,item的具体类就不相关了--我们知道它符合HasDataElement接口,所以我们可以调用item.getDataElement()。

代码语言:javascript
复制
private static void processAllDataElements(Map<String, List<? extends HasDataElement>> map) {
    for (List<? extends HasDataElement> list : map.values()) {
        for (HasDataElement item : list) {
            System.out.println(item.getDataElement());
        }
    }
}

示例用法

下面是一个简单的例子,以及输出,它创建了不同类A、B和C的几个不同的列表,然后创建了一个映射并添加了所有三个列表。

代码语言:javascript
复制
List<A> listOfA = List.of(new A[]{new A()});
List<B> listOfB = List.of(new B[]{new B(), new B()});
List<C> listOfC = List.of(new C[]{new C(), new C(), new C()});

Map<String, List<? extends HasDataElement>> map = new HashMap<>();
map.put("A", listOfA);
map.put("B", listOfB);
map.put("C", listOfC);

processAllDataElements(map);

A
B
B
C
C
C
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72847847

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档