我正在研究能够尽快检测圆圈碰撞的扫描线,我只是想知道是否有人知道更有效的方式而不是扫描线。我的代码更像是一个行线的混合,使用最大潜在的圆圈大小来移除活动圆圈,当它们不可能发生碰撞时。
如果有人知道更好或者可以给我反馈我实际上已经完成任务的效率,我将非常感激,这一次伤害了我的大脑只是想着它。
的Javascript
var Width = 1200
var Height = 1200
const svg = document.getElementById('svg1')
svg.setAttribute('width', Width)
svg.setAttribute('height', Height)
function seg(x, y, c) {
var segment = document.createElementNS("http://www.w3.org/2000/svg", "circle")
segment.setAttribute("cx", x)
segment.setAttribute("cy", y)
segment.setAttribute("r", c)
svg.appendChild(segment)
}
function seg2(x, y, c) {
var segment = document.createElementNS("http://www.w3.org/2000/svg", "circle")
segment.setAttribute("cx", x)
segment.setAttribute("cy", y)
segment.setAttribute("r", c)
segment.setAttribute('fill', '#0f0')
svg.appendChild(segment)
}
function seg3(x, y, c) {
var segment = document.createElementNS("http://www.w3.org/2000/svg", "circle")
segment.setAttribute("cx", x)
segment.setAttribute("cy", y)
segment.setAttribute("r", c)
segment.setAttribute('fill', '#ff0')
svg.appendChild(segment)
}
const circles = []
var addPoints = function(n) {
for (i = 0; i < n; i++) {
var o = {
x: Math.random() * 1000,
y: Math.random() * 1000,
c: (Math.random() * 5) + 5
}
circles.push(o)
seg(o.x, o.y, o.c)
}
}
addPoints(1000)
circles.sort(function(a, b) {
if (a.x > b.x) return 1
if (a.x < b.x) return -1
return 0
})
var peak = function(a) {
L = 0
for (i = 0; i < a.length; i++) {
if (a[i].c > L) {
L = a[i].c
}
}
return L
}
var sweep = function(J) {
var A = []
var M = peak(J)
for (i = 0; i < J.length; i++) {
if (A.length > 0) {
for (k = 0; k < A.length; k++) {
ea = A[k].x + A[k].c
jm = J[i].x - M
if (ea < jm) {
A.splice(k, 1)
} else {
bj = J[i].x - J[i].c
if ((bj - ea) < 0) {
yy = Math.abs(A[k].y - J[i].y)
yt = A[k].c + J[i].c
if (yy < yt) {
xx = J[i].x - A[k].x
yy = J[i].y - A[k].y
cc = Math.sqrt((xx * xx) + (yy * yy))
dd = J[i].c + A[k].c
if (cc < dd) {
seg2(A[k].x, A[k].y, A[k].c)
seg3(J[i].x, J[i].y, J[i].c)
}
}
}
}
}
}
A.push(J[i])
}
}
sweep(circles)
&#13;
<svg id="svg1"></svg>
&#13;
答案 0 :(得分:1)
单轴定理是这里的简单方法。对于圈子来说,它更容易;你只需要检查半径和圆圈之间的距离。这是一种平均在O(n log n)
时间内运行的方法:
2r
的四叉树中的所有位置。如果那里没有任何东西,并且没有其他圈子找到我们,那么这个圆圈不会与任何东西发生碰撞。