java替代使用嵌套for循环

Posted

技术标签:

【中文标题】java替代使用嵌套for循环【英文标题】:java alternative to using nested for loops 【发布时间】:2022-01-14 11:33:08 【问题描述】:

我有一个包含两个字段的策略对象:policyNumber 和 policyStatus。我将有一份保单列表,我需要查看是否有任何保单具有我提供的状态之一。如果有,我将布尔值设置为是。如果没有,我将其设置为否。

通常我会像这样使用嵌套的 for 循环:

Boolean hasStatus = false;
List<Policy> policies = new List<Policy>();
String[] statuses = String[]'A1','A3','B6','T1','T6';
for (Policy policy : policies) 
    for (int i=0; i<statuses.length; i++) 
        if (policy.policyStatus == statuses[i] 
            hasStatus = true;
            break;
            
    

return hasStatus;

现在我在涉及地图、集合和集合以及算法的领域非常周到。我想知道是否有一些事情是我应该做的,而不是使用嵌套的 for 循环和 if 块。如果有,请您给我一些指导吗?还是我真的应该这样做?

【问题讨论】:

请注意'A1' (etc) 不是Strings:您需要使用"A1",并带有双引号。此外,您几乎肯定不想使用==,而应该使用equals 还要注意break跳出当前循环。见***.com/questions/886955/… 【参考方案1】:

在深入研究之前,我想解决几个问题。

List 是一个接口,所以不能实例化这种类型的对象。但是,您可以使用 ArrayList 来实例化它。您不必直接使用policy.policyStatus 访问成员,您应该考虑使用getter 来确保封装,所以policy.getStatus()

使用过滤器和地图!正如安迪雄辩地所说,这是一个非常干净和优雅的解决方案。希望这也有帮助!

简短补充:我认为 java 流有时有点过于复杂,但它们非常有用。如果您使用.stream() 流式传输集合,这将使Java 逐个查看集合的每个成员。然后你可以使用一堆很酷的方法。

...stream().map() 只是将一个函数一个一个地应用于单个对象。这个功能可以是任何东西! java中的function接口有一个方法R apply(T t);——所以它接受一个输入,并产生一个输出。如您所见,R 类型的输出可能与 T 类型的输入不同。如果您不想返回任何内容,可以直接在集合上使用集合 forEach 方法。此方法采用consumer,类似于function,但它不返回任何内容。你也可以做...stream().filter(),它接受predicate,基本上是一个评估为真或假的问题。所有这些只是为了代码的简单性,java中的函数式编程实际上在野外非常有用:D

【讨论】:

感谢您指出语法错误!我的坏 :D 但是 a == b 总是错误的,在你的 ide 中尝试一下。字符串是对象,而不是文字。 哇,我不知道。我一直认为== 会返回 false(我可能从 uni 的早期误解了这一点)并且总是使用 .equals,感谢您指出我的错误。我在我的ide中重新运行了它!我会相应地改变我的答案。 我的立场是正确的。我删除了部分答案,感谢您指出:D 尽管如此,您是正确的,(几乎)总是equals 是比较字符串的正确方法【参考方案2】:

您可以将Policy 类实现为policyStatuspolicyNumber 的映射(在这种情况下policyStatus 是键policyNumberMap 的值)并像这样执行您的检查:

    Boolean hasStatus = false;
    Map<String, Integer> policyMap = getPolicyMap();
    String[] statuses = String[]"A1", "A3", "B6", "T1", "T6";
    for (String status : statuses) 
        if(policyMap.get(status) != null)
            hasStatus = true;
            break;
        
    
    
    return hasStatus;

或者如果你不能这样做并且你的statuses 的长度是恒定的或者长度上的上限很小,你不应该担心在你的项目中有一个带有嵌套循环的子例程。因为这是不可能的。你所做的是在n 的数组上搜索m 元素,没有任何先验条件或知识,你需要O(nm) 比较,所以你需要嵌套循环。但正如我所说,您可以使用 Map 数据结构重构您的代码并使用单循环。

【讨论】:

【参考方案3】:

构造一个包含状态的Set&lt;String&gt;

Set<String> statusSet = new HashSet<>(statuses);

然后使用流迭代policies

return policies.stream().anyMatch(p -> statusSet.contains(p.policyStatus));

【讨论】:

如果我们的数组有n 长度并且我们的列表有m,这个子例程仍然执行它与O(nm) 比较的工作,所以从技术上讲它是一个嵌套循环。我说的对吗? @Mahdi 我相信不是,HashSet 使用的哈希算法性能优于 O(n)(最终是恒定时间) @MahdiYusefi 在HashSet 中的查找是 O(1)。

以上是关于java替代使用嵌套for循环的主要内容,如果未能解决你的问题,请参考以下文章

java中for嵌套for循环的详细讲解?

JAVA里 FOR循环内 IF 与 ELSE的嵌套使用

小白学Java for循环3分钟学会Java的for循环,让看懂for循环嵌套再不是难事

Java for 嵌套循环

在 Java 8 中使用嵌套的 for 循环,找出给定的差异 [重复]

java,for循环嵌套,打印菱形