[路飞]_1046. 最后一块石头的重量

175 阅读1分钟

题目地址
B站地址

题目描述

有一堆石头,每块石头的重量都是正整数。

每一回合,从中选出两块 最重的 石头,然后将它们一起粉碎。假设石头的重量分别为 x 和 y,且 x <= y。那么粉碎的可能结果如下:

如果 x == y,那么两块石头都会被完全粉碎; 如果 x != y,那么重量为 x 的石头将会完全粉碎,而重量为 y 的石头新重量为 y-x。 最后,最多只会剩下一块石头。返回此石头的重量。如果没有石头剩下,就返回 0。

示例:

输出:1
解释:
先选出 7 和 8,得到 1,所以数组转换为 [2,4,1,1,1],
再选出 2 和 4,得到 2,所以数组转换为 [2,1,1,1],
接着是 2 和 1,得到 1,所以数组转换为 [1,1,1],
最后选出 1 和 1,得到 0,最终数组转换为 [1],这就是最后剩下那块石头的重量。

解题思路1

  • 先将传入的数组进行排序,最大的放在最前面
  • 遍历,遍历进行的条件是排序后的数组的长度大于1
  • 将数组的第一个元素拿出来,并且删除这个元素
  • 将返回后的新元素的第一个元素拿出来,并且删除这个元素
  • 每次拿出元素后,都删除元素,可以保证每次操作的元素都是最前面的两个
  • 判断拿出的元素的值是否相等,不等于就把差值添加到数组中,并执行排序
  • 最后循环跳出,数组的长度最后为0的话,那就返回0,数组的长度为1的话,就返回数组内的值

代码

var lastStoneWeight = function(stones){
    let newA = stones.sort((a, b) => (b -a));
    while(newA.lenght > 1){
        let x = newA[0];newA.shift();
        let y = newA[0];newA.shift();
        if(x != y){
            newA.push(x - y);
            newA = newA.sort((a,b) => (b - a));
        }
    }
    if(newA.length === 0) return 0;
    if(newA.lenght === 1) return newA[0];
}

解题思路2

  • 维护一个最大堆队列,将数组内的值放入最大堆队列
  • 拿出堆队列的前两个值做比较
var lastStoneWeight = function(stones){
    const pq = new MaxPriorityQueue();
    for(const stone of stones){
        pq.enqueue('x', stone);
    }
    while(pq.size() > 1){
        let a = pq.dequeue()['priority'];
        let b = pq.dequeue()['priority'];
        if(a > b){
            pq.enqueue('x, 'a - b');
        }
    }
    return pq.isEmpty() ? 0 : pq.dequeue()['priority'];
}