我的碰撞检测在 Java 小程序中生成低 fps
这是我第一次尝试碰撞算法。我尝试检查带有边界的对象的矩形大小。现在,在这个应用程序中,我制作了运行子弹并检查是否在无延时 while 循环中发生碰撞。问题是,当我生成大约 30-40 颗子弹时,FPS 变得如此之低。如果有人能教我一种编写碰撞检测的可靠方法,我会很高兴。
顺便说一句,我使用了一个java Vector集合(可能迭代不够快?或者我的代码太乱)
public void checkBoundary(int width, int height) //width and height of the applet
{
for(int i = 0; i < vec.size(); i++)
{
if(vec.get(i).x + vec.get(i).width <= 0 ||
vec.get(i).y + vec.get(i).height <= 0 ||
vec.get(i).x >= width ||
vec.get(i).y >= height)
vec.remove(i);
}
}
这个Vector存储了一个Bullet的对象,以(x,y)为左下角,并且(宽度,高度)。
This is my first time experimenting on collision algorithm. I tried checking the rect size of an object with the boundary. Now, in this application, I made running bullets and check if the collision in a no time-delay while loop. The problem is, as I spawn around 30-40 bullets, the fps gets so low. I would be glad if someone could teach me a robust way to write collision detection.
By the way, I used a java Vector collection (Maybe the iteration is not fast enough? or my code is being too messy)
public void checkBoundary(int width, int height) //width and height of the applet
{
for(int i = 0; i < vec.size(); i++)
{
if(vec.get(i).x + vec.get(i).width <= 0 ||
vec.get(i).y + vec.get(i).height <= 0 ||
vec.get(i).x >= width ||
vec.get(i).y >= height)
vec.remove(i);
}
}
This Vector store an object of Bullet with (x,y) as bottom-left corner, and (width,height).
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
首先,您的算法不正确,因为当您使用
vec.remove(i);
删除时,i+1
元素变为i
元素,因此你跳过一个元素。性能问题来自这样一个事实:在最坏的情况下,每个元素都会删除成本
O(n)
,因为每个后续元素都需要向左移动。试试这个:编辑:
正如 Frozen Spider 指出的那样,
removeAll
很昂贵。它的复杂度为O(outofbounds.size()*vec.size())
,即O(n^2)
。当稍微改变逻辑时,您可以导出一个保证在O(vec.size())
中工作的算法。First your algorithm is incorrect because when you remove using
vec.remove(i);
, thei+1
element become thei
element, so you skip one element.The performance issue come from the fact that on worst case each remove cost
O(n)
, as each subsequent element need to be shifted left. try this:Edit:
As Frozen Spider pointed out,
removeAll
is expensive. It has a complexity ofO(outofbounds.size()*vec.size())
, which isO(n^2)
. When slightly changing the logic you can derive an algorithm which is guaranteed to work inO(vec.size())
.remove()
是一项非常昂贵的操作,创建新列表、将所需元素复制到其中并用新列表替换原始列表要快得多。我还建议您使用 ArrayList 而不是 Vector。如果需要同步,请将
ArrayList
包装在Collections.synchronizedList()
中。试试这个,几乎可以立即工作 - <16 毫秒(0.016 秒)超过 100k 元素:
remove()
is a very costly operation, much faster will be to create new list, copy desired elements into it and replace original list with new one.I also recommend you to use
ArrayList
instead ofVector
. If you need synchronization, wrapArrayList
inCollections.synchronizedList()
.Try this, works almost instantly - <16 ms (0.016 sec) over 100k elements: