通过流API解释二进制到整数代码的解决方案

时间:2018-11-23 12:39:10

标签: java java-8

在解决代码战中的kata问题时,我遇到了单行解决方案,以解决将二进制数(以list的形式)转换为整数的问题。 我无法理解人们使用Java Stream api reduce函数的解决方案。请帮助我理解它。

例如:[0,0,0,1]被视为0001,它是1的二进制表示形式。

import java.util.List;

public class BinaryArrayToNumber {

    public static int ConvertBinaryArrayToInt(List<Integer> binary) {
       return binary.stream().reduce((x, y) -> x * 2 + y).get();
 }
}

3 个答案:

答案 0 :(得分:5)

首先,其背后的数学基于here

中描述的方法

借助示例可以最好地理解代码的工作。考虑二进制数1011(十进制11)

  • 操作按顺序流式传输。通过reduce操作的行为方式,我们将x重命名为accumulator,将y重命名为ele
  • 我们现在可以用数学方式将上述操作表示为

    accumulator = (accumulator*2)+ ele // refer here for why

  • 让公式在1011上运行

  • 流式传输从第一个元素(即左侧)开始,并按顺序进行
  • 开始:累加器= 0
  • 1)累加器=(0 * 2)+ 1 //第一个元素,累加器= 1
  • 2)累加器=(1 * 2)+ 0 //第二个元素,累加器= 2
  • 3)累加器=(2 * 2)+ 1 //第三个元素,累加器= 5
  • 4)累加器=(5 * 2)+ 1 //最后一个元素,累加器= 11

您可以将其扩展为n个二进制数字。

需要注意的重要一点是,尽管对于编码比赛来说这是可以的,但由于reduce()期望进行关联操作并且不能保证按顺序运行,因此不应在实际应用中使用它

答案 1 :(得分:0)

reduce函数的目的是使用给定的公式将流中的元素累积为单个结果。

对该流的每个元素重复执行此累积过程。最初,第一个参数(“ x”)取0,第二个参数(“ y”)取流中的第一个值。对于后续的每个步骤,上一次计算的结果将用作第一个参数,流中的下一个值将用作第二个参数。

使用过程编程,返回binary.stream()。reduce((x,y)-> x * 2 + y).get(); 与您的情况等效片段:

TableColumn<Person, Gender> genderColumn = new TableColumn<>("Gender");
genderColumn.setCellValueFactory(new PropertyValueFactory<>("gender"));
genderColumn.setCellFactory(col -> new GenderTableCell<>());

答案 2 :(得分:0)

reduce实际上使人们能够“减少”(也称为 fold accumulate )流元素成 single 值。


您无需查看reduce方法文档即可了解所采取的确切步骤:

它提供了一个示例,说明它等效于:

boolean foundAny = false;
T result = null;
for (T element : this stream) {
     if (!foundAny) {
         foundAny = true;
         result = element;
     }
     else
         result = accumulator.apply(result, element);
}
return foundAny ? Optional.of(result) : Optional.empty();

其中accumulator是您提供的功能,即(x, y) -> x * 2 + y