【问题标题】:How do I make for loops run side by side?如何让 for 循环并排运行?
【发布时间】:2008-11-08 06:45:55
【问题描述】:

我一直在做一个幼稚的小程序:屏幕上有一堆不同颜色和大小的小圆圈。当一个较大的圆圈遇到一个较小的圆圈时,它会吃掉较小的圆圈,当一个圆圈吃掉足够多的其他圆圈时,它就会繁殖。这有点整洁!

但是,我实现它的方式是,检测附近圆圈并检查它们是否可食用的过程是通过一个循环完成的循环完成的在开始下跌之前飙升至3000。这个过程不会让我的电脑变慢,我可以去玩《战争黎明》或其他什么的,而且没有任何变慢:它只是检查每个圈子看它是否与其他圈子发生碰撞的过程。 .

所以我想到的是,我可以尝试将应用程序窗口分成四个象限,并让象限中的圆圈同时进行检查,因为它们几乎没有机会相互干扰:或者什么达到那个效果!

那么,我的问题是:如何创建并排运行的 for 循环?比如说在 Java 中。

【问题讨论】:

  • 请记住,如果您更改 circles 程序以使其使用 CPU 上的所有内核,它可能会开始影响 Dawn of War。小心你想要的:-)
  • 这些圆圈在移动吗?随机?在我提出建议之前,我认为您需要先说一下。

标签: java loops


【解决方案1】:

你这里的问题其实不用线程就能解决的。

您需要的是空间数据结构。四叉树最好,或者如果球体移动的场是固定的(我假设是),您可以使用简单的网格。继承人的想法。

将显示区域划分为一个正方形网格,其中每个单元格至少与您最大的圆圈一样大。对于每个单元格,保留一个列表(最好是链表),其中包含中心在该单元格中的所有圆圈。然后在碰撞检测步骤中遍历每个单元格并检查该单元格中的每个圆圈与该单元格中的所有其他圆圈和周围的单元格。

从技术上讲,您不必检查每个单元格周围的所有单元格,因为其中一些单元格可能已经被检查过。

您可以将此技术与多线程技术相结合以获得更好的性能。

【讨论】:

    【解决方案2】:

    计算机通常是单任务的,这意味着它们通常可以在每个 CPU 或内核一次执行一条指令。

    但是,正如您所注意到的,您的操作系统(和其他程序)似乎同时运行许多任务。

    这是通过将工作拆分为进程来实现的,每个进程可以通过衍生线程来进一步实现并发。然后操作系统在每个进程和线程之间非常快速地切换,从而产生多任务的错觉。

    在您的情况下,您的 java 程序是单个进程,您需要创建 4 个线程,每个线程都运行自己的循环。这可能会变得很棘手,因为线程需要同步它们对局部变量的访问,以防止一个线程在另一个线程试图访问它时编辑变量。

    因为线程是一个复杂的主题,所以需要比我在这里做的更多的解释。

    不过,您可以阅读 Suns 关于并发的优秀教程,其中涵盖了您需要了解的所有内容:

    http://java.sun.com/docs/books/tutorial/essential/concurrency/

    【讨论】:

    • 只要知道这叫什么,这个“线程”,就足以让我开始了解它:谢谢!通常只是不知道某事的词是能够了解它与不了解它之间的障碍。
    • 哇!线程超出了我的范围:我阅读了该教程并将尝试使用线程编写我自己的东西,但我认为我还需要一段时间才能使用它们来加速碰撞检测。谢谢!
    【解决方案3】:

    您正在寻找的不是让这些同时运行的方法(正如人们所指出的,这取决于您拥有多少内核,并且只能提供 2 倍或 4 倍的加速),而是以某种方式削减减少您必须检测的碰撞次数。

    您应该考虑使用quadtree。简而言之,您递归地将您的 2D 区域分解为四个象限(根据需要),然后只需要检测附近组件中的对象之间的碰撞。在好的情况下,它可以有效地将你的碰撞检测时间从 N^2 减少到 N * log N。

    【讨论】:

      【解决方案4】:

      您可能希望寻找碰撞检测优化,而不是尝试进行并行处理。因为在很多情况下,在一个线程中执行较少的计算比在多个线程之间分配计算要好,而且在这种多线程业务中很容易自爆。尝试使用谷歌搜索“碰撞检测算法”,看看它在哪里;)

      【讨论】:

      • 嘿,当然。起初我让每个球检查对方的球,这意味着有些球正在检查已经被吃掉的球!我解决了这个问题,它帮助了很多人。我一定会用谷歌搜索你说的这些“碰撞检测算法”!
      【解决方案5】:

      如果您的计算机有多个处理器或多个内核,那么您可以轻松运行多个线程并在每个线程中运行较小的循环部分。如今,许多 PC 确实有多个内核 - 所以要有它,以便每个线程获得循环计数的 1/n,然后创建 n 个线程。

      【讨论】:

        【解决方案6】:

        如果你真的想进入并发编程,你需要学习如何使用线程。

        Sun 在这里有一个 Java 线程编程教程: http://java.sun.com/docs/books/tutorial/essential/concurrency/

        【讨论】:

          【解决方案7】:

          这听起来和我的一个实验很相似 - 看看...

          http://tinyurl.com/3fn8w8

          我对四叉树也很感兴趣(这就是我来这里的原因)...希望你明白了。

          【讨论】:

            猜你喜欢
            • 2016-05-27
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2019-07-03
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2022-10-09
            相关资源
            最近更新 更多