找到最接近原点(0,0)的K个点

时间:2019-02-05 23:16:44

标签: javascript arrays algorithm loops return

问题是,给定一个坐标列表,确定最接近原点的k个坐标。

我已经能够确定点与原点之间的距离,但是当筛选最接近的k点时,我迷路了。我决定将此逻辑放在第二个for循环中,对从最接近到最远的距离数组进行排序,然后推入小于K的值。

function kClosest(points, k) {
    let length = [];
    let arr = [];
    let result = [];
    let a = 0;
    let b = 0;

    for (let i = 0; i < points.length; i++) {
        a = points[i][0]; //x coord
        b = points[i][1]; //y coord (y will always be second number or '1')
        length.push(parseFloat(calcHypotenuse(a, b).toFixed(4)))
        arr.push([points[i], length[i]])
    }

    function calcHypotenuse(a, b) {
        return (Math.sqrt((a * a) + (b * b)));
    }

    for (let i = 0; i < k; i++) {
        arr = arr.sort();
        result.push(arr[i][0])
    }
    return result;
}



console.log(kClosest([
    [-5, 4],
    [-6, -5],
    [4, 6]
], K = 2))

预期输出:[-5,4],[4,6] //我有[-5,4],[-6,-5]

2 个答案:

答案 0 :(得分:4)

我建议为此使用自定义排序-您可以通过Array.sort()这样的比较函数:

function kClosest(points, k) {

    //sorts the array in place
    points.sort((point1, point2) => {
        const distanceFromOrigin1 = getDistanceFromOrigin(point1);
        const distanceFromOrigin2 = getDistanceFromOrigin(point2);

        //sort by distance from origin, lowest first
        return distanceFromOrigin1 - distanceFromOrigin2;
    });

    //returns first k elements
    return points.slice(0, k);
}

function getDistanceFromOrigin(point) {
    const [x, y] = point; //array destructuring
    return (x*x) + (y*y);
}

console.log(kClosest([
    [-5, 4],
    [-6, -5],
    [4, 6]
], 2))

有关自定义排序的更多详细信息,请参见https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort

答案 1 :(得分:2)

对整个数组进行排序很浪费,甚至可能无法实现。这是浪费的,因为该问题并没有要求所有元素,甚至没有k元素的总排序。使用基于比较的排序进行排序需要O(n log(n))时间。更一般而言,如果输入是数字流,那么甚至不可能将所有数字存储在内存中并对其进行排序。

我对JavaScript不太了解,但是在一般的算法草皮上,我们可以使用以下两种方法之一更快地解决此问题:

  1. 使用最大值Priority Queue:根据距原点的距离,按顺序创建最大值PQ。继续在最大PQ中插入元素,每当大小超过k时,都移除顶部元素(最大)。最后,PQ将具有k个最小的元素。空间复杂度:O(k),时间复杂度:O(n log(k)),对于k << n,可能接近O(n)
  2. 使用Quick-select:在输入上运行k次快速选择。假定输入适合内存(空间O(n)),但运行时间为O(nk),对于k << n,时间可能接近O(n)