首页 > 其他分享 >2024/07/28 每日一题

2024/07/28 每日一题

时间:2024-07-28 19:17:51浏览次数:10  
标签:07 int tree self 28 2024 lson positions left

LeetCode 699 掉落的方块

方法1:暴力

class Solution:
    def fallingSquares(self, positions: List[List[int]]) -> List[int]:
        n = len(positions); ans = [0] * n  # 记录每个方块落下后的高度
        for i, (left0, widen0) in enumerate(positions):
            height = widen0  # 默认
            right0 = left0 + widen0  # 右边界
            for j in range(i):  # 遍历前 i - 1 个判定叠加高度
                left, widen = positions[j]
                right = left + widen
                if  right0 > left and left0 < right:  # 当前方块会落在第 j 块的上方
                    height = max(height, ans[j] + widen0)
            ans[i] = height
        for i in range(1, n):
            ans[i] = max(ans[i - 1], ans[i])
        return ans
  • ArrayList 添加add() / 获取get() / 修改set()
class Solution {
    public List<Integer> fallingSquares(int[][] positions) {
        int n = positions.length;
        List<Integer> heights = new ArrayList<Integer>();
        for (int i = 0; i < n; i++) { // 对于每一个方块
            int left0 = positions[i][0];
            int right0 = positions[i][0] + positions[i][1];
            int height = positions[i][1];  // 默认高度
            for (int j = 0; j < i; j++) { // 遍历 i - 1 个方块
                int left = positions[j][0];
                int right = positions[j][0] + positions[j][1];
                if (right0 > left && left0 < right) 
                    height = Math.max(height, heights.get(j) + positions[i][1]);
            }
            heights.add(height);
        }
        for (int i = 1; i < n; i++) {
            heights.set(i, Math.max(heights.get(i - 1), heights.get(i)));
        }
        return heights;
    }
}

方法2:线段树

  • defaultdict 默认字典
class DynamicSegmentTree:
    """动态开点线段树模板 关键在于使用 defaultdict 来存储左右儿子"""

    def __init__(self):
        self.val = defaultdict(int)
        self.add = defaultdict(int)

    # 将区间 [L, R] 内的数据都更新为 v; o 的左右儿子 lson / rson
    def update(self, o: int, lson: int, rson: int, L: int, R: int, v: int) -> None:
        if L <= lson and rson <= R:  # 整个[lson, rson]需要修改
            self.do(o, v)
            return
        self.pushdown(o)  # 区间未覆盖 懒标记需要向下传递
        mid = (lson + rson) >> 1
        if mid >= L:  # [L, R] 区间包含了一部分左儿子
            self.update(o << 1, lson, mid, L, R, v)
        if mid < R:  # [L, R] 区间包含了一部分右儿子
            self.update(o << 1 | 1, mid + 1, rson, L, R, v)
        self.pushup(o)  # 将修改后的结果向上传递

    def pushup(self, o: int) -> None:
        self.val[o] = max(self.val[o << 1], self.val[o << 1 | 1])

    def pushdown(self, o: int) -> None:
        v = self.add[o]
        if v == 0:
            return
        self.do(o << 1, v)  # 给左儿子
        self.do(o << 1 | 1, v)  # 给右儿子
        self.add[o] = 0

    def do(self, o: int, v: int) -> None:
        self.val[o] = max(self.val[o], v)  # 本题存储的高度
        self.add[o] = max(self.add[o], v)

    # 查询区间 [L, R] 内的高度最大值
    def query(self, o: int, lson: int, rson: int, L: int, R: int) -> int:
        if L <= lson and rson <= R:
            return self.val[o]
        self.pushdown(o)  # 将懒标签向下传递
        res = 0; mid = (lson + rson) >> 1
        if mid >= L:
            res = self.query(o << 1, lson, mid, L, R)
        if mid < R:
            res = max(res, self.query(o << 1 | 1, mid + 1, rson, L, R))
        return res

class Solution:
    def fallingSquares(self, positions: List[List[int]]) -> List[int]:
        ans = list(); N = 10 ** 9 + 1; Max = 0  # 记录当前最高值
        st = DynamicSegmentTree()
        for left, widen in positions:
            # 查询 [left, left + widen - 1] 区间内高度的最大值
            curH = st.query(1, 1, N, left, left + widen - 1)
            Max = max(Max, curH + widen); ans.append(Max)
            # 更新 [left, left + widen - 1] 区间内的高度为 curH + widen
            st.update(1, 1, N, left, left + widen - 1, curH + widen)
        return ans
class Solution {
    class Node {
        int val, add;  // 存储的值和懒标记
        int lson, rson;  // 左右儿子所在下标
    }

    int N = 1000_000_000 + 1;  // 管辖区间的最大值
    int cnt = 0;  // 节点个数并在生成节点时完成节点之间的连接
    Node[] tree = new Node[1000010];

    // 更新 [L, R] 区间的值为 v; lson / rson 为 o 管辖的区间范围
    void update(int o, int lson, int rson, int L, int R, int v) {
        if (L <= lson && rson <= R) {
            work(o, v);
            return ;
        }
        pushdown(o);  // 将懒标记向下传递
        int mid = (lson + rson) >> 1;
        if (mid >= L)
            update(tree[o].lson, lson, mid, L, R, v);
        if (mid < R)
            update(tree[o].rson, mid + 1, rson, L, R, v);
        pushup(o);
    } 
    
    void pushup(int o) {
        tree[o].val = Math.max(tree[tree[o].lson].val, tree[tree[o].rson].val);
    }

    void work(int o, int v) {
        tree[o].val = Math.max(tree[o].val, v);
        tree[o].add = Math.max(tree[o].add, v);
    }

    void pushdown(int o) {
        // 当前节点未创建
        if (tree[o] == null) tree[o] = new Node();
        if (tree[o].lson == 0) {  // 左边空新建左节点
            tree[o].lson = ++cnt;
            tree[tree[o].lson] = new Node();
        }
        if (tree[o].rson == 0) {  // 右边空新建右节点
            tree[o].rson = ++cnt;
            tree[tree[o].rson] = new Node();
        }
        int v = tree[o].add;
        if (v == 0) return ;
        work(tree[o].lson, v);
        work(tree[o].rson, v);
        tree[o].add = 0;
    }

    // 查询 [L, R] 区间内高度最大值
    int query(int o, int lson, int rson, int L, int R) {
        if (L <= lson && rson <= R) 
            return tree[o].val;
        pushdown(o);
        int mid = (lson + rson) >> 1, res = 0;
        if (mid >= L)
            res = query(tree[o].lson, lson, mid, L, R);
        if (mid < R)
            res = Math.max(res, query(tree[o].rson, mid + 1, rson, L, R));
        return res;
    }

    public List<Integer> fallingSquares(int[][] positions) {
        List<Integer> ans = new ArrayList<>();
        tree[1] = new Node();  // tree[1].val 保存着实时最大值
        for (int[] info : positions) {
            int left = info[0], widen = info[1];
            int cur = query(1, 1, N, left, left + widen - 1);
            update(1, 1, N, left, left + widen - 1, cur + widen);
            ans.add(tree[1].val);
        }
        return ans;
    }
}

标签:07,int,tree,self,28,2024,lson,positions,left
From: https://www.cnblogs.com/XuGui/p/18328723

相关文章

  • LeetCode_sql_day07(579. 查询员工的累计薪水,2173.最多连胜的次数)
    描述:579.查询员工的累计薪水编写一个解决方案,在一个统一的表中计算出每个员工的 累计工资汇总 。员工的 累计工资汇总 可以计算如下:对于该员工工作的每个月,将 该月 和 前两个月 的工资 加 起来。这是他们当月的 3个月总工资和 。如果员工在前几个月没有为公......
  • 大创项目个人周报(2024.7.22—2024.7.28)
    本周个人情况汇报我本周主要学习了安卓开发的内容,根据《第一行代码Android》开展了学习。一、分析自己的第一个Android程序通过看书,我对项目的各个文件的功能有了大致了解,除app目录外,大多数文件和目录是自动生成的,app目录是今后开发工作主要涉及的部分。app的结构如下。......
  • 2024牛客多校第四场F.Good Tree 挑战全网最详解
    好吧标题党了一回,但我相信有不少人被出题人的那句“手玩一下就知道了”无语住了像我这种憨憨一旦想偏了就救不回来了,于是困惑了好久,在雨巨的指导下彻底搞懂(此处大声谢谢雨巨,又有实力又会讲题又认真答疑每一个问题,呜呜呜我永远的姐)题意简单来说就是定义f(i)为树上i点到其他所有......
  • Java基础07:基本运算符
    运算符运算符operatorJava语言支持如下运算符:算术运算符:+,-,*,/,%,++,--赋值运算符=关系运算符:>,<,>=,<=,==,!=instanceof逻辑运算符:&&,||,!位运算符:&,|,^,~,>>,<<,>>>(了解!!!)条件运算符?:扩展赋值运算符:+=,-=,*=,/=二元运算符publicstaticvoidmain(Str......
  • Adobe Photoshop 2024 v25.11 (macOS, Windows) - 照片和设计软件
    AdobePhotoshop2024v25.11(macOS,Windows)-照片和设计软件Acrobat、AfterEffects、Animate、Audition、Bridge、CharacterAnimator、Dimension、Dreamweaver、Illustrator、InCopy、InDesign、LightroomClassic、MediaEncoder、Photoshop、PremierePro、AdobeXD......
  • Adobe Illustrator 2024 v28.6 (macOS, Windows) - 矢量绘图
    AdobeIllustrator2024v28.6(macOS,Windows)-矢量绘图Acrobat、AfterEffects、Animate、Audition、Bridge、CharacterAnimator、Dimension、Dreamweaver、Illustrator、InCopy、InDesign、LightroomClassic、MediaEncoder、Photoshop、PremierePro、AdobeXD什么是......
  • 7月28日 竞彩足球!哈马比vs米亚尔比 维京vs莫尔德
    昨日复盘今日扫盘哈马比队,作为瑞典超级联赛的传统强队,凭借其在斯德哥尔摩索德尔体育场的主场优势,一直展现出强大的竞争力。本赛季,球队以稳定的表现,近6场联赛中取得了4胜1平1负的佳绩,防守端表现尤为出色,主场进攻力同样强劲。不过,在与米亚尔比队的交锋中,哈马比队本赛季首次对......
  • 在Windows下安装设置IDEA 2024.1.4
    文章目录下载IDEA安装IDEA设置IDEA汉化IDEA(可选)创建一个Java项目激活IDEA下载IDEAIDEA下载直链安装IDEA双击打开下载好的安装包,点击下一步更改你的安装目录,完成后下一步根据自己的需求来勾选安装选项,完成后下一步选择开始菜单目录,这里默认安装等待进度......
  • AI论文阅读笔记 | Timer: Generative Pre-trained Transformers Are Large Time Serie
    一、基本信息题目:Timer:GenerativePre-trainedTransformersAreLargeTimeSeriesModels会议:ICML2024原文:https://arxiv.org/abs/2402.02368源码:​​​​​​​https://github.com/thuml/Timer二、基本内容 1、解决什么问题虽然深度学习对时间序列的分析做出了显著......
  • 【嵌入式DIY实例-ESP8266篇】- LCD ST7789显示BME280传感器数据
    LCDST7789显示BME280传感器数据文章目录LCDST7789显示BME280传感器数据1、硬件准备2、代码实现本文将介绍如何使用ESP8266NodeMCU开发板(ESP12-E模块)和BME280气压、温度和湿度传感器构建一个简单的气象站。NodeMCU微控制器(ESP8266EX)从BME280......