为什么 String.chars() 是 Java 8 中的整数流? [英] Why is String.chars() a stream of ints in Java 8?

查看:38
本文介绍了为什么 String.chars() 是 Java 8 中的整数流?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在 Java 8 中,有一个新方法 String.chars() 返回表示字符代码的 ints (IntStream) 流.我想很多人会期望这里有一个 char 流.以这种方式设计 API 的动机是什么?

In Java 8, there is a new method String.chars() which returns a stream of ints (IntStream) that represent the character codes. I guess many people would expect a stream of chars here instead. What was the motivation to design the API this way?

推荐答案

正如其他人已经提到的,这背后的设计决策是为了防止方法和类的爆炸式增长.

As others have already mentioned, the design decision behind this was to prevent the explosion of methods and classes.

不过,我个人认为这是一个非常糟糕的决定,应该这样做,因为他们不想制作 CharStream,这是合理的,不同的方法而不是 chars(),我会想到:

Still, personally I think this was a very bad decision, and there should, given they do not want to make CharStream, which is reasonable, different methods instead of chars(), I would think of:

  • 流<字符>chars(),它给出了一个盒子字符流,这会带来一些轻性能损失.
  • IntStream unboxedChars(),用于性能代码.
  • Stream<Character> chars(), that gives a stream of boxes characters, which will have some light performance penalty.
  • IntStream unboxedChars(), which would to be used for performance code.

然而,与其关注为什么目前以这种方式完成,我认为这个答案应该侧重于展示一种使用我们拥有的 API 来做到这一点的方法使用 Java 8.

However, instead of focusing on why it is done this way currently, I think this answer should focus on showing a way to do it with the API that we have gotten with Java 8.

在 Java 7 中,我会这样做:

In Java 7 I would have done it like this:

for (int i = 0; i < hello.length(); i++) {
    System.out.println(hello.charAt(i));
}

而且我认为在 Java 8 中执行此操作的合理方法如下:

And I think a reasonable method to do it in Java 8 is the following:

hello.chars()
        .mapToObj(i -> (char)i)
        .forEach(System.out::println);

在这里我获得一个 IntStream 并通过 lambda i -> 将它映射到一个对象.(char)i,这会自动把它装箱成​​一个Stream,然后我们就可以为所欲为了,仍然使用方法引用作为加分项.

Here I obtain an IntStream and map it to an object via the lambda i -> (char)i, this will automatically box it into a Stream<Character>, and then we can do what we want, and still use method references as a plus.

注意虽然你必须mapToObj,但如果你忘记并使用map,那么什么都不会抱怨,但你仍然会得到一个 IntStream,而且你可能不知道为什么它打印整数值而不是代表字符的字符串.

Be aware though that you must do mapToObj, if you forget and use map, then nothing will complain, but you will still end up with an IntStream, and you might be left off wondering why it prints the integer values instead of the strings representing the characters.

Java 8 的其他丑陋替代品:

通过保留在 IntStream 中并希望最终打印它们,您不能再使用方法引用进行打印:

By remaining in an IntStream and wanting to print them ultimately, you cannot use method references anymore for printing:

hello.chars()
        .forEach(i -> System.out.println((char)i));

此外,对您自己的方法使用方法引用不再有效!考虑以下几点:

Moreover, using method references to your own method do not work anymore! Consider the following:

private void print(char c) {
    System.out.println(c);
}

然后

hello.chars()
        .forEach(this::print);

这会导致编译错误,因为可能存在有损转换.

This will give a compile error, as there possibly is a lossy conversion.

结论:

API之所以这样设计是因为不想添加CharStream,我个人认为该方法应该返回一个Stream,目前的解决方法是在 IntStream 上使用 mapToObj(i -> (char)i) 以便能够正常使用它们.

The API was designed this way because of not wanting to add CharStream, I personally think that the method should return a Stream<Character>, and the workaround currently is to use mapToObj(i -> (char)i) on an IntStream to be able to work properly with them.

这篇关于为什么 String.chars() 是 Java 8 中的整数流?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆