用于递归方法的Java 8实现

时间:2016-03-13 11:37:42

标签: java recursion lambda java-8

将lambdas用于递归方法的正确方法是什么?我一直在尝试为 Graph 编写深度优先搜索递归函数。我已经尝试实现Lambda版本,但不确定我的实现是否是在递归函数中使用它的正确方法。

代码大纲:

a)老式的方式

private void depthFirstSearch(final Graph graph, final int sourceVertex){
    count++;
    marked[sourceVertex]= true;
    for(int vertex:graph.getAllVerticesConnectedTo(sourceVertex)){
        if(marked[vertex]!=true){
            edgeTo[vertex]=sourceVertex;
            depthFirstSearch(graph,vertex);
        }
    }
}

b)Java 8 Lambdas方式:

private void depthFirstSearchJava8(final Graph graph, final int sourceVertex){
    count++;
    marked[sourceVertex]= true;
    StreamSupport.stream(graph.getAllVerticesConnectedTo(sourceVertex).spliterator(),false)
            .forEach(vertex -> {
                if(marked[vertex]!=true){
                    edgeTo[vertex]=sourceVertex;
                    depthFirstSearchJava8(graph,sourceVertex);
                }
            });
}

我试图像上面那样写一个lambda版本,但与传统方法相比,无法弄清楚它提供的优势。

由于

3 个答案:

答案 0 :(得分:1)

仅仅因为存在lambda,这并不意味着你必须在任何地方使用它们。

你循环遍历一个iterable,没有过滤或映射或转换任何东西(这是lambdas的典型用例)。

import Ionicons from 'react-native-vector-icons/Ionicons'; 循环在单行中执行您想要的操作。因此,不应该在这里使用lambda。

答案 1 :(得分:0)

那是因为没有优势,至少在这种情况下没有优势。当你想创建一个小函数只在程序中的一个地方使用时,Lambdas非常有用,例如:传递lambda作为另一个函数的参数时。如果你的lambda需要多行代码,你应该重新考虑使用它的想法。

答案 2 :(得分:0)

您可以按如下方式重写depthFirstSearch方法:

private void depthFirstSearchJava8(Graph graph, int sourceVertex){
    count++;
    marked[sourceVertex] = true;
    graph.getAllVerticesConnectedTo(sourceVertex).stream()
        .filter(vertex -> !marked[vertex])
        .peek(vertex -> edgeTo[vertex] = sourceVertex)
        .forEach(vertex -> depthFirstSearchJava8(graph, vertex));
}

此代码假定getAllVerticesConnectedTo()方法返回整数集合。如果它返回一个整数数组,则使用以下代码:

private void depthFirstSearchJava8(Graph graph, int sourceVertex){
    count++;
    marked[sourceVertex] = true;
    Arrays.stream(graph.getAllVerticesConnectedTo(sourceVertex))
        .filter(vertex -> !marked[vertex])
        .peek(vertex -> edgeTo[vertex] = sourceVertex)
        .forEach(vertex -> depthFirstSearchJava8(graph, vertex));
}

在第一个解决方案中,我使用Collection.stream()方法获取连接顶点流,而在第二个解决方案中,我使用了Arrays.stream()方法。然后,在这两个解决方案中,我首先使用filter()仅保留未标记的顶点,并使用peek()来修改edgeTo数组。最后,forEach()用于通过递归调用depthFirstSearchJava8()方法来终止流。