为 CompletableFuture 创建一个通用数组

ayu*_*hgp 8 java generics java-8

我需要创建一个通用的CompletableFuture对象数组,以便我可以将它传递给CompletableFuture.allOf方法CompletableFuture来同步线程。但由于它是通用的,我无法创建它。一个明显的解决方案是创建一个 List 然后调用toArray它,但效率很低。有没有更好的方法?这是我的代码:

// Current solution: 
List<CompletableFuture<List<ReportComparable>>> newReports = new ArrayList<>();

// Loop and add CompletableFuture objects to this list

// Collect all the retrieved objects here(Sync Threads).
    try {
        List<List<ReportComparable>> newReps = CompletableFuture.allOf((CompletableFuture<?>[]) newReports.toArray()).get();
    } catch (InterruptedException | ExecutionException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
Run Code Online (Sandbox Code Playgroud)

Hol*_*ger 5

你的问题有几个错误的假设

  • 你不能做(CompletableFuture<?>[]) newReports.toArray()。无参数toArray()方法将返回Object[]并且转换尝试将导致ClassCastException. 只有toArray(T[])接受现有数组的方法才会返回相同类型的数组,这会让您回到零方格

  • CompletableFuture.allOf返回 a CompletableFuture<Void>,因此您不能调用get()它并期望获得List<List<ReportComparable>>. 完成后您必须自己组装结果列表。

  • 当所有类型参数都是通配符时,创建泛型类的数组没有问题。所以

    CompletableFuture<?>[] array = new CompletableFuture<?>[100];
    
    Run Code Online (Sandbox Code Playgroud)

    作品。

  • 当您有任意数量的元素时,将它们添加到 aList并对其进行调用toArray,不一定效率低下。另一种方法是手动处理数组和索引,其作用与 相同ArrayList,但容易出错。的单个复制步骤toArray很少与性能相关。

    还请记住,由于CompletableFuture.allOf返回CompletableFuture<Void>您可能需要List<CompletableFuture<List<ReportComparable>>>无论如何才能List<List<ReportComparable>>在完成后构建所需的。

    另一方面,当您有固定数量的参数时,您可以直接调用varargs方法CompletableFuture.allOf,而无需手动创建数组。


但是,当您只想立即调用CompletableFuture返回的 by 时allOfget()“等待所有”操作无论如何都没有任何好处。

CompletableFuture通过get()or查询单个实例join()并将结果添加到 result 时,您会隐式获得相同的效果List,完成后您无论如何都必须这样做,因为CompletableFuture.allOf这对您不起作用。