gpt4 book ai didi

带有序列化的 Java 8 Lambda 表达式

转载 作者:IT王子 更新时间:2023-10-29 05:57:20 24 4
gpt4 key购买 nike

在我们的 Web 应用程序项目中,我们使用 Redis 来管理 session 。为了支持它,我们正在序列化将存储在 session 中的任何对象。

例如,我们使用 DTO 来保存用于在屏幕上显示的 bean 数据。即使 DTO 在 (Composition) 中有任何其他对象,我们也必须对其进行序列化,否则我们会得到 NotSerializableException

我在创建匿名内部类来实现 Comparator 时遇到问题,如下所示:

Collections.sort(people, new Comparator<Person>() {
public int compare(Person p1, Person p2) {
return p1.getLastName().compareTo(p2.getLastName());
}
});

上面的代码抛出了 NotSerializableException,我通过创建一个实现 ComparatorSerializable 接口(interface)的类来解决它。问题是,它被扔进了使用此 DTO 的 JSP 页面。我必须进行大量调试才能找到实际问题。

但是现在,我想更改上面的代码以使用如下所示的 Lambda 表达式:

Collections.sort(people, (p1, p2) -> p1.getLastName().compareTo(p2.getLastName()));

但是,我担心可能会发生同样的异常。 Lambda 表达式是否在内部创建对象?

最佳答案

您可以通过以下方式创建可序列化的 lambda 表达式

Collections.sort(people, (Comparator<Person>&Serializable)
(p1, p2) -> p1.getLastName().compareTo(p2.getLastName()));

但需要注意的是,通过

创建一个 Comparator
(p1, p2) -> p1.getLastName().compareTo(p2.getLastName())

带有不鼓励的冗余。您正在调用 getLastName() 两次,并且在任何一种情况下都必须注意在正确的参数变量上调用它。使用起来更直接

Comparator.comparing(Person::getLastName)

相反。您还可以使此比较器可序列化,尽管这意味着会失去很多简洁性:

Collections.sort(people,
Comparator.comparing((Function<Person,String>&Serializable)Person::getLastName));

这也更健壮。 lambda 表达式的序列化形式包含对实现方法的引用,在第一个变体中,它是一个合成方法,具有编译器生成的名称,当您在定义方法中使用另一个 lambda 表达式时,该名称可能会更改。相反,Person::getLastName 指向命名方法 getLastName 作为实现方法(至少使用 javac)。

但通常,可序列化的 lambda 表达式可能包含令人惊讶的编译器依赖项,应谨慎使用。

由于它们旨在描述行为而不是数据,因此长期存储它们毫无意义。对于在具有相同代码库的 JVM 之间传输它们,它们就足够了。

关于带有序列化的 Java 8 Lambda 表达式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41718021/

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