我有一个SalesOrders列表,包括Inactive和Active。我想遍历整个列表并设置每个SalesOrder处于活动状态的时间长度。 (该列表已由StartTime排序)
我的循环如下:
for(int i = 0; i < salesOrders.size(); i++) {
if(salesOrders.get(i).getStatus() == RecordStatus.ACTIVE) {
ELDDutyLog activeSalesOrder = salesOrders.get(i);
for(int j = i + 1; j < salesOrders.size(); j++) {
if(salesOrders.get(j).getStatus() == RecordStatus.ACTIVE) {
ELDDutyLog nextActiveSalesOrder = salesOrders.get(j);
salesOrders.get(i).setActiveDurationMinutes(
Minutes.minutesBetween(
activeSalesOrder.getStartTime(),
nextActiveSalesOrder.getStartTime()
).getMinutes()
);
break;
}
}
}
}
return salesOrders;
虽然这种方法有效,但我觉得必须有更好的方法来实现这一点,可能是使用Java 8?任何人都可以向我提出任何方向吗?
答案 0 :(得分:4)
每次跳过不活跃的销售订单时,您不必再次循环整个列表。相反,您可以过滤活动销售订单一次,然后您始终知道下一个活动销售订单是已过滤列表中的下一个订单。
像这样(未经测试):
List<ELDDutyLog> activeSalesOrders = salesOrders.stream()
.filter(so -> so.getStatus() == RecordStatus.ACTIVE)
.collect(Collectors.toList());
for (int i = 0; i < activeSalesOrders.size() - 1; i++) {
activeSalesOrders.get(i).setActiveDurationMinutes(
Minutes.minutesBetween(
activeSalesOrders.get(i).getStartTime(),
activeSalesOrders.get(i+1).getStartTime()
).getMinutes()
);
}
答案 1 :(得分:3)
我希望我理解正确。尝试(未测试):
salesOrders.stream()
.filter(salesOrder -> salesOrder.getStatus() == RecordStatus.ACTIVE)
.reduce((current, next) -> {
current.setActiveDurationMinutes(
Minutes.minutesBetween(
current.getStartTime(),
next.getStartTime()
).getMinutes()
);
return next;
});
说实话......对于reduce
来说这有点奇怪,但我认为它会起作用。
答案 2 :(得分:1)
无需嵌套两个循环;您搜索的nextActiveSalesOrder
计算setActiveDurationMinutes
调用的参数,与您在外循环的下一次迭代中搜索的activeSalesOrder
相同。除此之外,尽管您已将该值存储在salesOrders.get(i)
中,但您在内部操作中不必要地调用activeSalesOrder
。
ELDDutyLog activeSalesOrder = null;
for(ELDDutyLog nextActiveSalesOrder: salesOrders) {
if(nextActiveSalesOrder.getStatus() != RecordStatus.ACTIVE) continue;
if(activeSalesOrder != null)
activeSalesOrder.setActiveDurationMinutes(
Minutes.minutesBetween(
activeSalesOrder.getStartTime(),
nextActiveSalesOrder.getStartTime()
).getMinutes()
);
activeSalesOrder = nextActiveSalesOrder;
}
除此之外......什么样的API要求你写Minutes.minutesBetween(a, b).getMinutes()
之类的东西? API需要被告知您需要多少次分钟?
与java.time
比较:
ChronoUnit.MINUTES.between(a, b)
(已返回long
)或a.until(b, ChronoUnit.MINUTES)
(dito,仍然没有冗余)