算法打卡-leetcode-20210425

138 阅读2分钟

1. 接雨水
给定 n 个非负整数表示每个宽度为 1 的柱子的高度图,计算按此排列的柱子,下雨之后能接多少雨水。

/**
 * @param {number[]} height
 * @return {number}
 */
var trap = function (height) {
    let rain = 0;

    // 行分析(超出时间限制)
    // let maxHeight = Math.max(...height);
    // let temp = 0;
    // let flag = false;
    // for (let i = 1; i <= maxHeight; ++i) {
    //     flag = false;
    //     temp = 0;
    //     for (let j = 0; j < height.length; ++j) {
    //         if(flag && height[j] < i){
    //             temp++;
    //         }
    //         if(height[j] >= i){
    //             rain += temp;
    //             temp = 0;
    //             flag = true;
    //         }
    //     }
    // }

    // 列分析
    // let leftIndex = 0;
    // let rightIndex = 0;
    // for (let i = 0; i < height.length; ++i) {
    //     if (height[i] >= height[leftIndex]) {
    //         leftIndex = i;
    //         continue;
    //     }
    //     if (i + 1 < height.length) {
    //         rightIndex = i;
    //         for (let j = i + 1; j < height.length; ++j) {
    //             if (height[j] >= height[rightIndex]) {
    //                 rightIndex = j;
    //             }
    //         }
    //         if (rightIndex > i) {
    //             minHeight = height[leftIndex] > height[rightIndex] ? height[rightIndex] : height[leftIndex];
    //             rain += (minHeight - height[i]);
    //         }
    //     }
    // }

    // 动态规划
    // let maxLeft = [...height];
    // let maxRight = [...height];
    // for (let i = 0; i < height.length; ++i) {
    //     if (maxLeft[i - 1] && maxLeft[i - 1] > maxLeft[i]) {
    //         maxLeft[i] = maxLeft[i - 1];
    //     }
    // }
    // for (let j = height.length - 1; j >= 0; --j) {
    //     if (maxRight[j + 1] && maxRight[j + 1] > maxRight[j]) {
    //         maxRight[j] = maxRight[j + 1];
    //     }
    // }
    // for(let x = 0; x < height.length; ++x){
    //     rain += Math.min(maxLeft[x], maxRight[x]) - height[x];
    // }

    // 双指针
    // let maxLeft = 0;
    // let maxRight = 0;
    // let leftIndex = 0, rightIndex = height.length - 1;
    // while (leftIndex < rightIndex) {
    //     if (height[leftIndex] < height[rightIndex]) {
    //         maxLeft = Math.max(maxLeft, height[leftIndex]);
    //         rain += (maxLeft - height[leftIndex]);
    //         ++leftIndex;
    //     } else {
    //         maxRight = Math.max(maxRight, height[rightIndex]);
    //         rain += (maxRight - height[rightIndex]);
    //         --rightIndex;
    //     }
    // }

    // 单调栈
    let stack = [];
    const length = height.length;
    for (let i = 0; i < length; ++i) {
        while (stack.length && height[i] > height[stack[stack.length - 1]]) {
            const top = stack.pop();
            if (!stack.length) {
                break;
            }
            const left = stack[stack.length - 1];
            const currWidth = i - left - 1;
            const currHeight = Math.min(height[i], height[left]) - height[top];
            rain += (currWidth * currHeight);
        }
        stack.push(i);
    }


    return rain;
};

2. 动物收容所
动物收容所。有家动物收容所只收容狗与猫,且严格遵守“先进先出”的原则。在收养该收容所的动物时,收养人只能收养所有动物中“最老”(由其进入收容所的时间长短而定)的动物,或者可以挑选猫或狗(同时必须收养此类动物中“最老”的)。换言之,收养人不能自由挑选想收养的对象。请创建适用于这个系统的数据结构,实现各种操作方法,比如enqueue、dequeueAny、dequeueDog和dequeueCat。允许使用Java内置的LinkedList数据结构。

enqueue方法有一个animal参数,animal[0]代表动物编号,animal[1]代表动物种类,其中 0 代表猫,1 代表狗。

dequeue*方法返回一个列表[动物编号, 动物种类],若没有可以收养的动物,则返回[-1,-1]。

var AnimalShelf = function () {
    this.array = [];
};

/** 
 * @param {number[]} animal
 * @return {void}
 */
AnimalShelf.prototype.enqueue = function (animal) {
    this.array.push(animal);
};

const dequeue = (array, type) => {
    let result = {
        array: [],
        animal: []
    }

    if (array.length > 0) {
        let animal;
        let temp = [];
        while (array.length > 0) {
            animal = array.shift();
            if (animal[1] === type) {
                break;
            } else {
                temp.push(animal);
            }
        }
        temp.push(...array);
        result.array = [...temp];
        if (animal[1] !== type) {
            result.animal = [-1, -1];
        } else {
            result.animal = animal;
        }
        return result;
    }
    result.array = array;
    result.animal = [-1, -1];
    return result;
}

/**
 * @return {number[]}
 */
AnimalShelf.prototype.dequeueAny = function () {
    if (this.array.length) {
        return this.array.shift();
    } else {
        return [-1, -1];
    }
};

/**
 * @return {number[]}
 */
AnimalShelf.prototype.dequeueDog = function () {
    result = dequeue([...this.array], 1);
    this.array = result.array;
    return result.animal;
};

/**
 * @return {number[]}
 */
AnimalShelf.prototype.dequeueCat = function () {
    result = dequeue([...this.array], 0);
    this.array = result.array;
    return result.animal;
};

/**
 * Your AnimalShelf object will be instantiated and called as such:
 * var obj = new AnimalShelf()
 * obj.enqueue(animal)
 * var param_2 = obj.dequeueAny()
 * var param_3 = obj.dequeueDog()
 * var param_4 = obj.dequeueCat()
 */