【问题标题】:Why does this Guava Ordering of a Map by value work?为什么这种按值对地图进行番石榴排序有效?
【发布时间】:2013-08-08 18:42:06
【问题描述】:

我是 Guava 库的新手,并尝试使用它的一些类来简化我的代码。我遇到了按值对 Map 进行排序的需要。快速搜索找到了this post,它发布了一个接受的答案,代码如下:sn-p:

Ordering<Map.Entry<Key, Value>> entryOrdering = Ordering.from(valueComparator)
  .onResultOf(new Function<Entry<Key, Value>, Value>() {
    public Value apply(Entry<Key, Value> entry) {
      return entry.getValue();
    }
  }).reverse();
// Desired entries in desired order.  Put them in an ImmutableMap in this order.
ImmutableMap.Builder<Key, Value> builder = ImmutableMap.builder();
for (Entry<Key, Value> entry : 
    entryOrdering.sortedCopy(map.entrySet())) {
  builder.put(entry.getKey(), entry.getValue());
}
return builder.build();
// ImmutableMap iterates over the entries in the desired order

有人可以为我澄清一下这是如何工作的吗?我有些不明白。

Ordering 的定义是Ordering&lt;T&gt;。在这种情况下,&lt;T&gt; 将是 Map.Entry。此外,onResultOf 的方法签名是onResultOf(Function&lt;F,? extends T&gt; function)

在上面的代码中,onResultOf 使用以下参数被调用:

onResultOf(new Function<Entry<Key, Value>, Value>())

在这种情况下意味着:

<F> = Entry<Key, Value>
<? extends T> = Value

这又意味着Value 是一种可以扩展Map.Entry 的类型。

这怎么可能?当入口映射包含 Key、Value 时,Value 怎么可能是扩展 Map.Entry 的类型?

我确信我误读或误解了某些东西,但如果有人能对此有所了解,我希望它能帮助我更好地理解 Guava 和 Ordering() 类。尤其是 onResultOf(Function) 的工作原理。

【问题讨论】:

    标签: java generics guava


    【解决方案1】:

    这里创建了三个不同的 Ordering,其中一个的类型与其他的不同。你的代码代码改写为:

    Ordering<Value> valueOrdering = Ordering.from(valueComparator);
    Ordering<Map.Entry<Key, Value>> entryOrdering = valueOrdering
         .onResultOf(new Function<Entry<Key, Value>, Value>() {
             public Value apply(Entry<Key, Value> entry) {
                return entry.getValue();
             }
    });
    Ordering<Map.Entry<Key, Value>> finalOrdering = entryOrdering.reverse();
    

    【讨论】:

      【解决方案2】:

      onResultOf的方法签名是:

      public <F> Ordering<F> onResultOf(Function<F,? extends T> function)
      

      F 代替了T。为了匹配之前的定义,它应该被重写为

      public <T> Ordering<T> onResultOf(Function<T,? extends U> function)
      

      所以onResultOf的参数实际上是Function&lt; Map.Entry&lt;Key, Value&gt;, ? extends U &gt;,因此第二个参数不必扩展Map.Entry

      【讨论】:

        【解决方案3】:

        也许你对 Ordering 类被声明为 Ordering&lt;T&gt; 的事实感到困惑,但 onResultOf 方法的返回值是 Ordering&lt;F&gt;

        您提供给onResultOfFunction 的第一个类型参数是结果的类型参数。

        这也意味着,Value 不会强制成为Map.Entry 的子类型。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2013-01-16
          • 1970-01-01
          • 1970-01-01
          • 2013-08-23
          • 1970-01-01
          • 2013-03-22
          • 1970-01-01
          相关资源
          最近更新 更多