如何将流转换为增强循环

时间:2018-09-25 06:52:09

标签: java

我已经开始使用Java 8并尝试将某些流转换为增强循环。

因此,例如,我正在尝试将此流转换为for循环,但是我做得不正确:

List<Job> jobs = shipment.getJobs();
Job shoppingJob = jobs.stream().filter(job -> job.isShopping()).findFirst().orElse(null);
Job deliveryJob = jobs.stream().filter(job -> job.isDelivery() || job.isRanger()).findFirst().orElse(null);

我想知道是否可以将上述示例转换为增强的for循环。到目前为止,我尝试像这样转换我的for循环代码:

 List<Job> jobs = shipment.getJobs();
 Job shoppingJob = null;
 Job deliveryJob = null;
 Job rangerJob = null;
    if(jobs != null || jobs.isEmpty()) {
        for (Job job : jobs) {
            if (job.isShopping()) {
                shoppingJob = job;
            } else {
                if (job.isDelivery()) {
                    deliveryJob = job;
                }
            }
        }
    }

4 个答案:

答案 0 :(得分:2)

您应将break用于findFirst功能。

下面是发现shoppingJob破损的情况。

Job shoppingJob = null;
if (jobs != null || jobs.isEmpty()) {
    for (Job job : jobs) {
        if (job.isShopping()) {
            shoppingJob = job;
            break;
        }
    }
}

下面是发现deliveryJob破损

Job deliveryJob = null;
if (jobs != null || jobs.isEmpty()) {
    for (Job job : jobs) {
        if (job.isShopping() || job.isRanger()) {
            deliveryJob = job;
            break;
        }
    }
}

但是您想要找到一个foor loop,您也可以这样做;

if (jobs != null || jobs.isEmpty()) {
    for (Job job : jobs) {
        if (!shoppingJobFound && job.isShopping()) {
            shoppingJob = job;
            shoppingJobFound = true;
        }
        if (!deliveryJobFound && (job.isDelivery() || job.isRanger())) {
            deliveryJob = job;
            deliveryJobFound = true;
        }
        if (shoppingJobFound && deliveryJobFound) {
            break;
        }
    }
}

答案 1 :(得分:1)

findFirst的意义在于,Stream管道将仅评估Stream的元素,直到找到第一个匹配元素(通过过滤器)为止。

将其转换为for循环时,一旦找到匹配项,就应退出循环。但是,由于要将两个Stream流水线转换为单个for循环,因此只有在找到两个条件都匹配后,才应该中断循环。

List<Job> jobs = shipment.getJobs();
Job shoppingJob = null;
Job deliveryJob = null;
if (jobs != null) {
    for (Job job : jobs) {
        if (shoppingJob == null && job.isShopping()) { // this is the first shopping job
            shoppingJob = job;
            if (deliveryJob != null) { // we can break after finding a match for both conditions
                break;
            }
        }
        if (deliveryJob == null && (job.isDelivery() || job.isRanger())) { // this is the first delivery or range job
            deliveryJob = job;
            if (shoppingJob != null) { // we can break after finding a match for both conditions
                break;
            }
        }
    }
}

答案 2 :(得分:1)

我看到您发布的代码有几个问题。这是应该执行的代码

    if(jobs != null) {
        for (Job job : jobs) {
            if (shoppingJob == null && job.isShopping()) {
                shoppingJob = job;
            } 
            else if (deliveryJob == null && (job.isDelivery() || job.isRanger())) {
                deliveryJob = job;
            }
        }
    }

所以需要改变的东西:

1)。如果作业列表为NullPointerException,则第一个if条件的第二部分将引发null。你有

if(jobs != null || jobs.isEmpty()) {

翻译为:如果不是null的工作进入该区块,或者如果null是工作,则在isEmpty()上调用jobs(然后调用{{1} isEmpty()上的}将引发null)。正如您在评论中指出的,NullPointerException也是多余的。

相反,我认为这就是您所需要的

isEmpty()

2)。如果要从流代码中获得与 if(jobs != null) { 相同的值,则必须确保一次为变量shoppingJobdeliveryJob赋值后,它们不会被覆盖。 。

否则,如果列表中有一个以上的购物任务或一个以上的交付任务,则这些变量实际上将最终分配给列表中的最后一个匹配任务,而不是第一个。这就是为什么需要这些条件的第一部分,即在本示例中为findFirst()

的原因
shoppingJob == null

3)。无需在else子句中编写if嵌套,如果需要条件else语句,则可以只使用if (shoppingJob == null && job.isShopping()) { 。尽管在这种情况下,为了完全符合逻辑,您根本不应该使用else if(在原始Streams代码中,如果作业为elseisShopping返回了true,则相同作业可以分配给两个变量,但是如果您在此处使用else,则只能分配给一个变量)

所以代替这个

isDelivery

您可以只使用if语句(没有其他内容)

else {
          if (deliveryJob == null && (job.isDelivery() || job.isRanger())) {

4)。最后,在原始代码中,您尝试复制,if (deliveryJob == null && (job.isDelivery() || job.isRanger())) { 被分配给为deliveryJobisDelivery()返回true的作业。在for循环代码中,您只检查了isRanger()

希望有帮助。

答案 3 :(得分:0)

已解决。谢谢

我只需要在nullshoppingJob的每种条件下检查deliveryJob。将会是:

 List<Job> jobs = shipment.getJobs();
    Job shoppingJob = null;
    Job deliveryJob = null;
    Job rangerJob = null;
    for (Job job : jobs) {
        if (shoppingJob == null && job.isShopping()) {
            shoppingJob = job;
        }
        if (deliveryJob == null && (job.isDelivery())) {
            deliveryJob = job;
        }
    }