307 区域和检索

307. 区域和检索 - 数组可修改 本题涉及到动态更新数组元素并频繁查询区间和的问题。可以采用线段树(Segment Tree)或树状数组(Binary Indexed Tree,Fenwick Tree)来解决。树状数组在处理单点更新和区间查询问题上有较好的时间复杂度,并且代码实现相对简洁。树状数组是一种用于高效处理单点更新和区间查询的数据结构。它通过二进制的特性,将数组划分为不同的区间,每个节点存储一定区间的和。题目编号和名称:307. 区域和检索 - 数组可修改。,请你完成两类查询。更新树状数组相关节点。前缀和相减得到区间和。 阅读详情

四种方法。

方法1:
直接暴力,sumRange o(n),update为o(1),如果k次操作均是求和,则时间复杂度为o(kn),难以承受

class NumArray {
    vector<int> v;
public:
    NumArray(vector<int>& nums) {
        for(int i :nums) v.push_back(i);
    }
    
    void update(int i, int val) {
        v[i] = val;
    }
    
    int sumRange(int i, int j) {
        int sum = 0;
        for(int k = i; k<= j; ++k)
            sum += v[k];
        return sum;
    }
};

方法2:
使用前缀和维护sum[i]
sumRange时间复杂度是o(1),但是update时间复杂度为o(n),如果k次操作均是求和,时间复杂度为o(kn)

class NumArray {
    vector<int> arr, sum;
public:
    NumArray(vector<int>& nums) {
        if(nums.size() == 0) return;
        arr = nums;
        sum.resize(nums.size());
        fill(sum.begin(), sum.end(), 0);
        sum[0] = nums[0];
        for(int i = 1; i < nums.size(); ++i)
            sum[i] = sum[i - 1] + nums[i];
    }
    
    void update(int i, int val) {
        for(int k = i; k < sum.size(); ++k)
            sum[k] += (val - arr[i]);
        arr[i] = val; // 修改之
    }
    
    int sumRange(int i, int j) {
        if(i == 0) return sum[j];
        else return sum[j] - sum[i - 1];
    }
};

方法3:

树状数组,tree[i]存放的是i号位之前lowbit(i)个元素之和,update和sumRange均为logn

class NumArray {
    vector<int> arr, tree; // tree树状数组,注意树状数组下标比原数组多1
public:
    NumArray(vector<int>& nums) {
        arr.resize(nums.size() + 1);
        tree.resize(nums.size() + 1); // 树状数组下标从1开始
        fill(arr.begin(), arr.end(), 0);
        fill(tree.begin(), tree.end(), 0); // 初始化arr和树状数组为0
        for(int i = 0; i < nums.size(); ++i)    
            update(i, nums[i]); // 初始化树状数组
    }
    
    inline int lowbit(int x) //求得能整除x的最大的2的幂次
    {
        return x & (-x);
    }

    void update(int i, int val) { // 向后更新,注意下标
        for(int j = i + 1; j < tree.size(); j += lowbit(j))
            tree[j] += (val - arr[i + 1]);
        arr[i + 1] = val; // 修改该位置
    }
    
    int getSum(int x) // 获得x位置之前的元素和,向前求和
    {
        int sum = 0;
        for(int k = x + 1; k >= 1; k -= lowbit(k))
            sum += tree[k];
        return sum;
    }

    int sumRange(int i, int j) { 
        return getSum(j) - getSum(i - 1); // 得到区间和
    }
};

方法4:
线段树,sumRange (logn), update(logn)

int n; // 全局变量作为默认参数
class NumArray{
    vector<int> tree; // tree线段树存放和,arr存放原数组
public:
    NumArray(vector<int>& nums) {
        if(nums.size() == 0) return;
        n = nums.size() - 1;
        tree.resize(4 * nums.size()); // 4倍原数组
        build_tree(nums); // 根节点下标为0
    }
    
    // left-right二分区间,cur为当前的tree的下标
    void build_tree(const vector<int>& arr, int cur = 0, int left = 0, int right = n) 
    {
        if(left == right)
        {
            tree[cur] = arr[left];
            return;
        }
        int mid = (left + right) >> 1;
        int l_child = 2 * cur + 1, r_child = 2 * cur + 2;
        build_tree(arr, l_child, left, mid);
        build_tree(arr, r_child, mid + 1, right);
        tree[cur] = tree[l_child] + tree[r_child];
    }

    // 区间搜索依赖于原数组的下标,更新依赖于线段树
    void update(int i, int val, int cur = 0, int left = 0, int right = n) {
        if(left == right)
        {
            tree[cur] = val;
            return;
        }
        int mid = (left + right) >> 1;
        int l_child = 2 * cur + 1, r_child = 2 * cur + 2;
        if(i >= left && i <= mid) // 要更新的位置落在原数组左半区,更新左子树及其路径
            update(i, val, l_child, left, mid);
        else update(i, val, r_child, mid + 1, right);
        tree[cur] = tree[l_child] + tree[r_child]; //修改完后更新线段树
    }
    
    int sumRange(int i, int j, int cur = 0, int left  = 0, int right = n) {
        if(right < i || left > j) return 0; // 不在查询区间内
        if(left >= i && right <= j) return tree[cur]; // 包含当前区间则直接返回
        int mid = (left + right) >> 1;
        int l_child = 2 * cur + 1, r_child = 2 * cur + 2;
        return sumRange(i, j, l_child, left, mid) + sumRange(i, j, r_child, mid + 1, right);
    }
};
22、用户界面流程(UI Flow)全解析 本文全面解析了用户界面流程(UI Flow)的概念、创建步骤及其在系统设计中的应用。通过示例和操作步骤,详细介绍了如何确定屏幕范围、识别屏幕、创建过渡和标记触发器,并阐述了UI Flow在导航识别、验证、可用性优化、测试用例开发和需求推导中的重要作用。文章还结合问答系统案例,展示了UI Flow的实际应用价值,帮助读者深入理解并有效运用这一工具提升系统用户体验。 阅读详情

相关推荐

LangChain + PlayWright实战:5分钟搞定网页自动化测试(附完整代码)

本文详细介绍了如何利用LangChain与PlayWright构建智能网页自动化测试系统。通过环境配置、核心架构设计、实战Agent构建及性能优化等步骤,开发者可以快速实现高效的Web操作自动化,提升测试效率。文章还提供了完整代码示例和典型问题解决方案。

weixin_27791839的博客 239

307. 区域和检索 - 数组可修改(JS实现)

1 题目 给定一个整数数组 nums,求出数组从索引 i 到 j (i ≤ j) 范围内元素的总和,包含 i, j 两点。 update(i, val) 函数可以通过将下标为 i 的数值更新为 val,从而对数列进行修改。 示例: Given nums = [1, 3, 5] sumRange(0, 2) -> 9 update(1, 2) sumRange(0, 2) -> 8 说明: 数组仅可以在 update 函数下进行修改。 你可以假设 update 函数与 sumRange 函

zjw_python的博客 532

机械臂学习:视觉引导——绪论

视觉引导 = 定位 + 引导定位:视觉系统定位到待引导的物体引导:视觉系统引导机械臂按需要的轨迹实现一定的工艺流程(过度点:人为指定机械臂的轨迹防止碰撞)(点云匹配:解决位姿估计姿态估计的问题)无序抓取的三个核心技术:3d识别(图中的点云匹配) 抓取方法路径规划(防止机械臂的碰撞,如自身碰撞等)如果只有同一高度的平移和旋转,其实并不需要点云,用单目就可以做,但是如果涉及到物体的倾斜以及高度的变换,那就是单目力所不能及,所以就是第三种情况:平移旋转加垫高。

2303_80018785的博客 4044

LeetCode第307题_区域和检索-数组可修改

LeetCode第307题"区域和检索 - 数组可修改"考察数组动态更新与区间查询的设计。文章详解四种解法:暴力法(更新O(1),查询O(n))、分块处理(更新O(1),查询O(√n))、树状数组和线段树(均更新O(logn),查询O(logn)),并对比各方法的性能特点。代码实现涵盖C#、Python和C++三种语言,适用于不同场景需求。文章还指出常见错误,如累加数组无法高效更新、分块大小不当等问题,帮助读者规避陷阱。

qq_40263592的博客 1380

Unity URP项目里Post Processing死活没效果?别急,这5个坑我帮你踩过了

本文详细解析了Unity URP项目中Post Processing效果不显示的5个常见问题及解决方案,包括管线配置、Volume设置、摄像机选项、Layer冲突和Shader兼容性。通过专业排查步骤和实用代码片段,帮助开发者快速定位并修复后处理效果失效问题,提升项目开发效率。

weixin_28693309的博客 233

从零拆解快手Web端__NS_hxfalcon:JS逆向签名参数定位与复现

在JS逆向与前端反爬攻防中,签名参数总是绕不开的核心环节。无论是接口加密还是请求签名,其本质都是通过在客户端收集环境信息、时间戳与业务参数,经特定算法计算后生成用于服务端校验的动态令牌。理解这类参数的生成原理,不仅能提升逆向分析效率,也能帮助前端开发者更好地设计自身接口防护方案。在实际工程中,面对经Webpack打包且高度混淆的代码,直接全局搜索参数名往往难以奏效,需要结合请求抓包、调用栈跟踪、环境适配等方法逐步定位。此类签名参数广泛存在于现代Web应用的GraphQL或REST接口中,是接口数据安全的重要

weixin_29474431的博客 336

Java实现 LeetCode 307 区域和检索 - 数组可修改

307. 区域和检索 - 数组可修改 给定一个整数数组 nums,求出数组从索引 i 到 j (i ≤ j) 范围内元素的总和,包含 i, j 两点。 update(i, val) 函数可以通过将下标为 i 的数值更新为 val,从而对数列进行修改。 示例: Given nums = [1, 3, 5] sumRange(0, 2) -> 9 update(1, 2) sumRange...

南 墙 1万+

使用DeepSeek、MCP和AKShare实现智能金融问答系统技术方案

DeepSeek是由深度求索公司开发的大规模语言模型,最新版本DeepSeek-V3采用混合专家(MoE)架构,拥有671B参数,激活37B参数,在多项基准测试中表现优异3。要使用DeepSeek的API服务:访问DeepSeek平台注册账号获取API Key(形如AKShare是基于Python的金融数据接口库,提供股票、基金、期货、宏观经济等领域的海量数据。主要特点包括:免费开源,数据源丰富支持多种数据格式(DataFrame/JSON)持续更新维护安装命令。

Kin 3172

LeetCode307——区域和检索 - 数组可修改

我的LeetCode代码仓:https://github.com/617076674/LeetCode 原题链接:https://leetcode-cn.com/problems/range-sum-query-mutable/description/ 题目描述: 知识点:线段树 思路:线段树 本题是LeetCode303——区域和检索的加强版,由于新增了update()操作,Lee...

清风阁 811

Unity URP热扭曲效果实战:如何让半透明物体也‘动’起来(附完整Shader代码)

本文深入解析Unity URP管线中热扭曲效果无法影响半透明物体的核心原因,并提供一套完整的实战解决方案。通过编写自定义Shader,并巧妙利用URP的Render Objects渲染器功能,成功让指定半透明物体(如粒子特效)也能被扭曲效果影响,从而制作出火焰、热浪等更具视觉冲击力的特效。文末附有完整的Shader代码与进阶优化技巧。

pz890123的博客 501

【nnUNetv2进阶】四、nnUNetv2 魔改网络-小试牛刀-加入注意力机制ChannelAttention

本文介绍了在nnunet中加入ChannelAttention的方法,按照本文教的教程,可以快速完成ChannelAttention的加入和自定义模型的跑通。

AI爱好者的博客,分享计算机领域相关知识 5800

线段树 307. 区域和检索 - 数组可修改

307. 区域和检索 - 数组可修改 给定一个整数数组 nums,求出数组从索引 i 到 j (i ≤ j) 范围内元素的总和,包含 i, j 两点。 update(i, val) 函数可以通过将下标为 i 的数值更新为 val,从而对数列进行修改。 示例: Given nums = [1, 3, 5] sumRange(0, 2) -> 9 update(1, 2) sumRange(0, 2) -> 8 说明: 数组仅可以在 update 函数下进行修改。 你可以假设 update

BLUEsang的博客 224

Far planner 代码系列(33) 关于real_world_contour和contour_graph

我们知道far planner前部分的流程是这样子的: 对于特定的地图,如下: 我们要从surround_obs_cloud里抽取生成realworld_contour_,如下图所示: 在这时候,每个node的z坐标都是以机器人的高度定的。如图所示: 先去吃饭啦~待会回来在写 ...

博客 762

【LeetCode】307 . 区域和检索 - 数组可修改

day203,树状数组完整思路

weixin_43894455的博客 544

Outlook Express 6 (OE6) for Win7/Win8/Win10

英文版 Outlook Express6.0, 兼容Win7/Win10/WinXP,解压就可用。

Statistics and Machine Learning Toolbox

Statistics and Machine Learning Toolbox(带书签),MATLAB统计学习工具

LeetCode 307. 区域和检索 - 数组可修改

307. 区域和检索 - 数组可修改题解 题目来源:307. 区域和检索 - 数组可修改 2022.04.04 每日一题

小明不要写Bug的博客 950

LinePhone3.2.7(android端最新版本) sip客户端

SIP客户端For android:LinePhone3.2.7(最新版本),官网地址:http://www.linphone.org/

leetcode-307:区域和检索 - 数组可修改

给你一个数组nums,请你完成两类查询。

菊头蝙蝠的博客 412

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

Leetcode307. 区域和检索 - 数组可修改(C语言)

Leetcode307. 区域和检索 - 数组可修改(C语言) 题目: 给定一个整数数组 nums,求出数组从索引 i 到 j (i ≤ j) 范围内元素的总和,包含 i, j 两点。update(i, val) 函数可以通过将下标为 i 的数值更新为 val,从而对数列进行修改。例: 输入:[“NumArray”,“sumRange”,“update”,“sumRange”] [[[1,3...

jeanlu的博客 371

[LeetCode解题报告] 307. 区域和检索 - 数组可修改

单点更新,区间求和,这种问题可以用线段树和树状数组做

liuliangcan的博客 190

【中等】力扣算法题解析LeetCode307:区域和检索-数组可修改

LeetCode307题解:树状数组实现动态区间和。本题要求实现支持单点更新和区间查询的数据结构。采用树状数组(BIT)高效处理: 树状数组特性: 通过二进制索引(lowbit)实现O(log n)的更新和查询。 索引从1开始,原数组i对应BIT的i+1。 核心操作: update:计算变化量,自底向上更新关联节点。 sumRange:通过前缀和差值(query(right+1)-query(left))获取区间和。

ylumwd的博客 601

leetcode:307. 区域和检索 - 数组可修改

本次要解决的问题是:单点修改+区间查询(区间和)

OceanStar的博客 365

Leetcode.307 区域和检索 - 数组可修改

解释: NumArray numArray = new NumArray([1, 3, 5]);numArray.sumRange(0,// 返回 1 + 3 + 5 = 9 numArray.update(1, 2);// 返回 1 + 2 + 5 = 8。对于单点修改,要修改的值为。,请你完成两类查询。

感觉画质不如...原神的博客 146

LeetCode-307. 区域和检索 - 数组可修改

307. 区域和检索 - 数组可修改 难度中等80收藏分享切换为英文关注 通过次数 4,680 提交次数 9,083 题目描述 评论 (56) 题解(20)New 提交记录 给定一个整数数组 nums,求出数组从索引i到j(i≤j) 范围内元素的总和,包含i, j两点。 update(i, val)函数可以通过将下标为i的数值更新为val,从而对...

保持对编程的热情! 243
上一篇: 212 单词搜索II
下一篇: 315 计算右侧小于当前元素的个数
UnendingGlory
博客等级 码龄9年 55粉丝 49原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值