如何使用Java 8和lambdas打印JVM的系统属性?

fge*_*fge 8 java lambda java-8

您可以使用以下方法获取PropertiesJVM属性的实例System.getProperties(); 您将如何使用Java 8代码将所有属性打印到控制台?

fge*_*fge 8

一个解决方案

public final class Foo
{
    private static void printProperty(final Object key, final Object value)
    {
        System.out.println(key + ": " + value);
    }

    public static void main(final String... args)
    {
        System.getProperties().forEach(Foo::printProperty);
    }
}
Run Code Online (Sandbox Code Playgroud)

撞倒:

  • Properties扩展Hashtable<Object, Object>自己实现Map<Object, Object>;
  • Map有一个.forEach()方法,其参数是a BiConsumer;
  • BiConsumer是一个功能界面 ;
  • printProperty()类的静态方法Foo碰巧具有与a相同的签名BiConsumer<Object, Object>:它的"返回值"是void,它的第一个参数是Object,它的第二个参数是Object;
  • 因此我们可以Foo::printProperty用作方法参考.

较短的版本是:

public final class ShorterFoo
{
    public static void main(final String... args)
    {
        System.getProperties()
            .forEach((key, value) -> System.out.println(key + ": " + value));
    }
}
Run Code Online (Sandbox Code Playgroud)

在运行时,这不会产生任何影响.请注意第二个示例中的类型推断:编译器可以推断出它key并且value是类型Object.写这个"匿名lambda"的另一种方法是:

(Object key, Object value) -> System.out.println(key + ": " + value)
Run Code Online (Sandbox Code Playgroud)

(不是这样)旁注:即使它有点过时,你真的想看这个视频(是的,这是一个小时的长度;是的,值得一看).


(没有的话)附注2:你可能已经注意到Map.forEach()提到了一个默认的实现 ; 这意味着您的自定义Map实现或外部库的其他实现将能够使用.forEach()(例如,Guava的ImmutableMap).存在许多关于Java集合的此类方法; 不要犹豫,对"老狗"使用这些"新方法".


Rad*_*def 5

@fge已经错过了一个非常短的版本,这个版本肯定取决于它的toString实现Map.Entry.

public class VeryShortFoo {
    public static void main(String... args) {
        System.getProperties().entrySet().forEach(System.out::println);
    }
}
Run Code Online (Sandbox Code Playgroud)
  • 在这里,entrySet流式传输,每个Map.Entry都打印参考out.println.
  • Map.EntrytoString一般返回的实现getKey() + "=" + getValue().

这是我非常喜欢的另一个.

public class ElegantFoo {
    public static void main(String... args) {
        System.getProperties().entrySet().stream()
            .map(e -> e.getKey() + ": " + e.getValue())
            .forEach(System.out::println);
    }
}
Run Code Online (Sandbox Code Playgroud)
  • entrySet再次(显式调用到了这个时候流stream).
  • Stream#map执行从一种类型的元素到另一种类型的元素的1:1转换.在这里,它变成了Stream<Map.Entry>一个Stream<String>.
  • 所述Stream<String>被打印.