如何在Java 8中减少这个重复的代码?

huangapple go评论73阅读模式
英文:

How can i reduce this repeat code in Java 8?

问题

我有以下的代码,它一直重复很多次。也许有一种方法可以减少它,但我不太了解Java。它看起来像这样:

public Optional<byte[]> generateReportA(List<ClassThatChange> request){
    if(CollectionUtils.isEmpty(request)) {
       return Optional.empty();
    }
    
    List<ClassThatNOChange> list = new ArrayList<>();

    
    for(ClassThatChange item : request){
        ClassThatNOChange c = new ClassThatNOChange()
        
        //这是从一个报告到另一个报告会改变的代码行
        c.setResult(callMethodA(item.getVariable1(), item.getVariable2()));

        list.add(c);
    }
    
    return Optional.of(callSameMethod(list));
}

public Optional<byte[]> generateReportB(List<ClassThatChange> request){
    if(CollectionUtils.isEmpty(request)) {
       return Optional.empty();
    }
    
    List<ClassThatNOChange> list = new ArrayList<>();

    
    for(ClassThatChange item : request){
        ClassThatNOChange c = new ClassThatNOChange()
        
        //这是从一个报告到另一个报告会改变的代码行
        c.setResult(callMethodB(item.getVariable2()));

        list.add(c);
    }
    
    return Optional.of(callSameMethod(list));
}

唯一会改变的是callMethodAcallMethodB等,但它们都返回相同类型的答案。

ClassThatChange 类似于这样:

public class Father{
      private Date date;
      // 然后是 getters 和 setters
}

public class Son extends Father{
      private String description;
      // 然后是 getters 和 setters
}

所有可以改变的类都扩展自Father

有没有一种方法可以减少这种重复的代码?
对不起,我的英语不太好。

英文:

I have the following code that keeps repeating a lot. Maybe there is a way to reduce it but i dont know too much of java. It looks like this:

public Optional&lt;byte[]&gt; generateReportA(List&lt;ClassThatChange&gt; request){
        if(CollectionUtils.isEmpty(request)) {
		   return Optional.empty();
	    }
        
        List&lt;ClassThatNOChange&gt; list = new ArrayList&lt;&gt;();

        
        for(ClassThatChange item : request){
            ClassThatNOChange c = new ClassThatNOChange()
            
            //here is the line of code that changes from report to report
            c.setResult(callMethodA(item.getVariable1(), item.getVariable2()));

            list.add(c);
        }
        
        return Optional.of(callSameMethod(list));
}

public Optional&lt;byte[]&gt; generateReportB(List&lt;ClassThatChange&gt; request){
        if(CollectionUtils.isEmpty(request)) {
		   return Optional.empty();
	    }
        
        List&lt;ClassThatNOChange&gt; list = new ArrayList&lt;&gt;();

        
        for(ClassThatChange item : request){
            ClassThatNOChange c = new ClassThatNOChange()
            
            //here is the line of code that changes from report to report
            c.setResult(callMethodB(item.getVariable2()));

            list.add(c);
        }
        
        return Optional.of(callSameMethod(list));
}

The only thing that change is the callMethodA, or B, or C... but all of them return the same type of answer.

The ClassThatChange is something like this:

public class Father{
      private Date date;
      // then the getters and setters
}

public class Son extends Father{
      private String description;
      // then the getters and setters
}

All the classes that can change extends from the father.

Is there a way to reduce this repeat code?
Sorry for my bad English.

答案1

得分: 2

我认为你正在寻找的是一种方法,可以将每种情况中的类型转换为始终相同的类型。这可以通过Function或者你自己定义的自定义函数接口来实现。在这里,我展示了Function

private <T> Optional<byte[]> convert(
    List<? extends T> request, 
    Function<? super T, ? extends SomeTypeYouDidNotShow> conversion) {

    if (request.isEmpty()) return Optional.empty();
    List<ClassThatNOChange> list = request.stream()
        .map(item -> {
                ClassThatNOChange c = new ClassThatNOChange();
                c.setResult(conversion.apply(item));
                return c;
            })
        .collect(Collectors.toList());
    return Optional.of(callSameMethod(list));
}

然后,你所有的重复方法都会类似于这样:

public Optional<byte[]> generateReportA(List<Father> request) {
    return convert(request, 
        item -> callMethodA(item.getVariable1(), item.getVariable2()));
}

public Optional<byte[]> generateReportB(List<Son> request) {
    return convert(request, 
        item -> callMethodB(item.getVariable2()));
}
英文:

I think what you are looking for is a way to plug in a conversion from the type that changes in each case to the type that is always the same. That could be done with a Function, or with a customized functional interface that you define. Here, I'm showing Function.

private &lt;T&gt; Optional&lt;byte[]&gt; convert(
    List&lt;? extends T&gt; request, 
    Function&lt;? super T, ? extends SomeTypeYouDidNotShow&gt; conversion) {

    if (request.isEmpty()) return Optional.empty();
    List&lt;ClassThatNOChange&gt; list = request.stream()
        .map(item -&gt; {
                ClassThatNOChange c = new ClassThatNOChange();
                c.setResult(conversion.apply(item));
                return c;
            })
        .collect(Collectors.toList());
    return Optional.of(callSameMethod(list));
}

Then all your duplicate methods would look something like this:

public Optional&lt;byte[]&gt; generateReportA(List&lt;Father&gt; request) {
    return convert(request, 
        item -&gt; callMethodA(item.getVariable1(), item.getVariable2()));
}

public Optional&lt;byte[]&gt; generateReportB(List&lt;Son&gt; request) {
    return convert(request, 
        item -&gt; callMethodB(item.getVariable2()));
}

huangapple
  • 本文由 发表于 2020年8月4日 08:42:23
  • 转载请务必保留本文链接:https://go.coder-hub.com/63238740.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定