gpt4 book ai didi

Java 8 将列表减少为链表

转载 作者:行者123 更新时间:2023-12-02 04:29:06 25 4
gpt4 key购买 nike

我的问题基本上归结为将 List 减少为链接列表,但从reduce 函数推断出的类型似乎不正确。

我的列表将如下所示

[0, 1, 2]

我希望reduce函数在每个reduce步骤中执行此操作

null                            // identity (a Node)
Node(0, null) // Node a = null, int b = 0
Node(1, Node(0, null)) // Node a = Node(0, null), int b = 1
Node(2, Node(1, Node(0, null))) // Node a = Node(1, Node(0, null)), int b = 2

但是,reduce 函数似乎认为这行不通,因为我猜它不认为身份是节点。

这是我的代码。

import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class Example {
static class Node {
int value;
Node next;

public Node(int value, Node next) {
this.value = value;
this.next = next;
}
}

static Node reverse(List<Integer> list) {
return list.stream()
.reduce(null, (a, b) -> new Node(b, a)); // error: thinks a is an integer
}

void run() {
List<Integer> list = IntStream.range(0, 3)
.boxed()
.collect(Collectors.toList());
Node reversed = reverse(list);
}

public static void main(String[] args) {
new Example().run();
}
}

我做错了什么?

编辑在接受答案后,我的代码如下所示:

import java.util.List;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class Example {
static class Node {
int value;
Node next;

public Node(int value, Node next) {
this.value = value;
this.next = next;
}

@Override
public String toString() {
return "Node{" +
"value=" + value +
", next=" + next +
'}';
}
}

static Node reverse(List<Integer> list) {
return list.stream()
.reduce(null, (n, i) -> {
System.out.println("Will happen"); // to demonstrate that this is called
return new Node(i, n);
}, (n1, n2) -> {
System.out.println("Won't happen"); // and this never is
return new Node(n1.value, n2);
});
}

void run() {
List<Integer> list = IntStream.range(0, 3)
.boxed()
.collect(Collectors.toList());
Node reversed = reverse(list);
System.out.println(reversed);
}

public static void main(String[] args) {
new Example().run();
}
}

现在可以打印了

Will happen
Will happen
Will happen
Node{value=2, next=Node{value=1, next=Node{value=0, next=null}}}

我仍然不知道为什么 Java 不能告诉 reduce 函数的第三个参数是不必要的,并且它永远不会被调用,但这是另一天的问题。

第二次编辑

可以为像这样的reduce操作创建一个新方法,因为reduce的第三个参数可以只是一个不执行任何操作的函数。

static <T, U> U reduce(Stream<T> stream, U identity, BiFunction<U, ? super T, U> accumulator) {
return stream.reduce(identity, accumulator, (a, b) -> null);
}

static Node reverse(List<Integer> list) {
return reduce(list.stream(), null, (n, i) -> new Node(i, n));
}

最佳答案

您可以使用其他归约运算符,执行

    static Node reverse(List<Integer> list) {
return list.stream()
.reduce(
(Node) null, //the empty element
(n, i) -> new Node(i, n) , //combining a Node and an Integer
(n1, n2) -> new Node(n1.value, n2)); // could be anything
}

编辑:使其与parallelStream一起使用:

    public static Node merge(Node n1, Node n2) {
if (n1 == null) {
return n2;
} else {
return new Node(n1.value, merge(n1.next, n2));
}
}

static Node reverse(List<Integer> list) {
return list.stream()
.reduce(
(Node) null, //the empty element
(n, i) -> new Node(i, n) , //combining a Node and an Integer
(n1, n2) -> merge(n1, n2)); // combining two Nodes
}

关于Java 8 将列表减少为链表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38167535/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com