Java 8中的map签名:public <U> Optional<U> map(Function<? super T,? extends U> mapper)--为什么有两个U?

6
public<U> Optional<U> map(Function<? super T, ? extends U> mapper)

为什么有两个 U?

我理解第二个 U...可选项具有描述返回的可选项类型的参数。

但我不明白前导的 U 是什么意思。我在调用带有以下内容的可选项的 map 方法时遇到了困难:

[javac]  return LocationAPIResponse.map(response -> Context.LocationContext.builder()...
[javac]                                            ^
[javac]  no instance(s) of type variable(s) U exist so that Optional<U> conforms to LocationContext
[javac]  where U,T are type-variables:
[javac]     U extends Object declared in method <U>map(Function<? super T,? extends U>)
[javac]     T extends Object declared in class Optional

我很困惑,因为我在map中定义的函数返回一个由builder创建的LocationContext。我对两个“U”感到困惑。编译器为什么会抱怨?
编辑,完善代码示例以更加完整:
Optional<LocationServiceResponse> locationAPIResponse = locationServiceProxy.getLocation(locationServiceRequest);
    return locationAPIResponse.map(response -> Context.LocationContext
        .builder()
       .isNearby(response.getProximity().equals(ProxyEnum.NEARBY) ? 1 : 0)
       .lat(response.getLatitude().orElse(0))
       .lng(response.getLongitude().orElse(0))
       .build());

你的名为 map 的函数预期执行什么操作? 考虑它返回一个 Optional ,这对于 map 操作很奇怪(其名称来自函数式编程)。此外,.build() 的返回类型是什么? - Ryan Leach
@RyanTheLeach 他正在使用一个 Optional 对象,并在其上调用 map() 方法。 - GhostCat
但是,Ryan是正确的:我认为你应该向我们展示**build()**的签名。对于一个mcve,你可能只需要builder.build()...你在那里设置对象并不重要,问题在于build方法到底返回了什么。嗯,准确地说:具有此返回语句return locationAPIResponse.map()的方法的签名也很重要。关键是编译器无法将您对map()的使用与使用返回值的方法的签名“连接”起来! - GhostCat
2个回答

6

这只是一个用于方法局部泛型类型的语法。

通过直接在方法签名中声明,可以将U绑定到此方法的上下文中。

您在泛型参数不能或不应该在类级别上知道的情况下使用它(例如,当您有一个需要泛型参数的静态方法时)。

对于编译器错误,我们需要更多信息。到目前为止唯一能说的是:使用给定的返回语句 return locationAPIResponse.map() ... 的方法的签名与您的映射器返回的内容不匹配!


嘿,谢谢!我大致理解你的意思,尽管我们肯定处于我 Java 能力的边缘。你能解释一下为什么编译失败吗?据我所知,LocationContext 的类型是 U。我查看了地图实现,它最终将返回值包装在 Optional 中,所以我不明白它还想要我做什么。 - David Massey
1
为此,我们可能需要更多上下文([mcve]),主要是尝试使用该方法的客户端代码。似乎您将map()作为一个类的静态方法调用,但它没有被声明为静态?因此,对于编译器错误,除非您允许我们帮助,否则我们无法提供帮助... - GhostCat
1
不好意思,这很误导人。我在遵循驼峰命名方面非常懒惰,而LocationAPIResponse实际上是一个Optional类型的局部变量。我会尝试编辑并创建一个更健壮、更简洁、更完整和可验证的示例。 - David Massey

0

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接