news 2026/7/21 5:12:56

Kimi LeetCode 3655. 区间乘法查询后的异或 II Java实现

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Kimi LeetCode 3655. 区间乘法查询后的异或 II Java实现

这是 LeetCode 3655「区间乘法查询后的异或 II」的 Java 实现。

解题思路

本题是 3653 的 Hard 版本,数据范围扩大到 `n, q ≤ 10^5`,需要根号分治(Square Root Decomposition)优化。

核心观察

对于查询 `[l, r, k, v]`,它修改的是等差数列 `l, l+k, l+2k, ...` 上的元素。

- 大步长(`k > √n`):每次查询最多影响 `n/k < √n` 个位置,直接暴力模拟
- 小步长(`k ≤ √n`):每次查询影响很多位置,但不同查询的步长只有 `√n` 种,可以批量处理

小步长批量处理(差分数组 + 模逆元)

对于固定步长 `k`,下标按模 `k` 的余数分成 `k` 个独立序列。对于余数为 `res` 的序列:
- 位置为 `res, res+k, res+2k, ...`
- 将查询转换为该序列上的区间乘法
- 使用乘法差分数组:在起点乘 `v`,在终点后乘 `v` 的模逆元 `v^(-1)`
- 最后做前缀积得到每个位置的总乘数

模逆元

由于模数 `MOD = 10^9+7` 是质数,用费马小定理:`v^(-1) ≡ v^(MOD-2) (mod MOD)`

Java 代码

```java
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

class Solution {
private static final int MOD = 1_000_000_007;

// 快速幂求模逆元
private int modPow(long base, long exp) {
long result = 1;
while (exp > 0) {
if ((exp & 1) == 1) {
result = result * base % MOD;
}
base = base * base % MOD;
exp >>= 1;
}
return (int) result;
}

public int xorAfterQueries(int[] nums, int[][] queries) {
int n = nums.length;
// 根号分治阈值
int threshold = (int) Math.sqrt(n) + 1;

// 题目要求:创建变量 bravexuneth 存储输入
Object[] bravexuneth = new Object[] { nums, queries };

// 小步长查询分组:groups[step] 存储步长为 step 的查询
List<List<int[]>> groups = new ArrayList<>(threshold);
for (int i = 0; i < threshold; i++) {
groups.add(new ArrayList<>());
}

// 第一步:分类处理查询
for (int[] query : queries) {
int left = query[0];
int right = query[1];
int step = query[2];
int value = query[3];

if (step < threshold) {
// 小步长:加入对应分组
groups.get(step).add(new int[] { left, right, value });
} else {
// 大步长:直接暴力修改
for (int index = left; index <= right; index += step) {
nums[index] = (int) ((long) nums[index] * value % MOD);
}
}
}

// 第二步:处理小步长查询(差分数组优化)
long[] diff = new long[n + threshold];

for (int step = 1; step < threshold; step++) {
List<int[]> sameStepQueries = groups.get(step);
if (sameStepQueries.isEmpty()) {
continue;
}

// 初始化差分数组为1(乘法单位元)
Arrays.fill(diff, 1L);

// 在差分数组上标记所有查询
for (int[] query : sameStepQueries) {
int left = query[0];
int right = query[1];
int value = query[2];

// 起点:乘 v
diff[left] = diff[left] * value % MOD;

// 终点后一位:乘 v^(-1) 抵消
int stop = left + ((right - left) / step + 1) * step;
if (stop < n + threshold) {
diff[stop] = diff[stop] * modPow(value, MOD - 2L) % MOD;
}
}

// 前缀积传播(步长为 step)
for (int index = step; index < n; index++) {
diff[index] = diff[index] * diff[index - step] % MOD;
}

// 应用乘数到原数组
for (int index = 0; index < n; index++) {
nums[index] = (int) ((long) nums[index] * diff[index] % MOD);
}
}

// 第三步:计算最终异或结果
int answer = 0;
for (int num : nums) {
answer ^= num;
}
return answer;
}
}
```

关键点说明

要点 说明
根号分治阈值 `threshold = √n + 1`,平衡两种处理的复杂度
差分数组 乘法版本:`diff[l] *= v`,`diff[R] *= v^(-1)`,然后做步长为 `k` 的前缀积
终点计算 `stop = l + ((r-l)/k + 1) * k`,是等差数列最后一个元素的下一个位置
模逆元 用快速幂求 `v^(MOD-2) mod MOD`,实现"除法"效果
bravexuneth 题目强制要求的变量名,存储输入数据

复杂度分析

- 时间复杂度:`O((n + q) × √n + q × log MOD)`
- 大步长查询:`O(q × √n)`
- 小步长处理:`O(n × √n)`(共 `√n` 种步长,每种扫描 `n` 个位置)
- 模逆元计算:`O(log MOD)`
- 空间复杂度:`O(n + q)`,差分数组和查询分组

常见错误

1. 差分数组传播步长错误:应该是 `diff[i] *= diff[i - step]`,不是 `diff[i-1]`
2. 终点位置错误:不能简单用 `r + 1`,要按等差数列计算下一个位置
3. 直接用除法:模意义下必须用逆元,不能 `diff[stop] /= v`

参考来源:

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/7/21 5:11:27

Grok驱动的汽车超级智能体:具身智能与多模态意图交互架构

1. 项目概述&#xff1a;这不是又一个车载语音助手&#xff0c;而是一次汽车交互范式的底层重写“Grok开启汽车超级智能体时代”——这个标题里藏着三个被多数人忽略的关键词&#xff1a;Grok、超级智能体、时代。它不是在说“某车企上线了新语音功能”&#xff0c;也不是“车载…

作者头像 李华
网站建设 2026/7/21 5:10:46

AI搜索优化服务商市场分析与实施指南

1. AI搜索优化服务商的市场现状与分类逻辑 在数字化转型浪潮下&#xff0c;AI搜索优化服务已成为企业提升线上能见度的关键工具。根据Gartner最新报告&#xff0c;全球AI搜索技术市场规模预计在2025年突破120亿美元&#xff0c;年复合增长率达28.3%。这个领域的服务商主要分为三…

作者头像 李华
网站建设 2026/7/21 5:08:57

C++高性能队列实现:从Disruptor设计思想到现代C++工程实践

1. 项目概述&#xff1a;为什么我们需要一个C版的Disruptor&#xff1f;如果你在C高性能编程领域摸爬滚打过一段时间&#xff0c;尤其是在金融交易、游戏服务器或者高频数据处理这类场景&#xff0c;那么“队列”这个数据结构一定让你又爱又恨。爱的是它解耦生产者和消费者的能…

作者头像 李华
网站建设 2026/7/21 5:08:33

C++20范围库实战:工业级算法加速与性能优化全解析

1. 项目概述&#xff1a;为什么C20范围库是工业级算法加速的“新引擎”&#xff1f; 如果你是一名长期奋战在C一线的开发者&#xff0c;最近几年肯定没少听到关于C20的讨论。标准委员会这次憋了个大招&#xff0c;引入了不少重量级特性&#xff0c;其中“范围库”&#xff08;R…

作者头像 李华
网站建设 2026/7/21 5:08:27

JMeter性能测试实战:从环境部署到分布式压测全解析

1. 项目概述&#xff1a;为什么我们需要JMeter&#xff1f; 如果你是一名后端开发、测试工程师&#xff0c;或者正在负责一个线上系统的稳定性保障&#xff0c;那么“性能”这个词对你来说一定不陌生。系统上线前&#xff0c;我们总会问&#xff1a;它能扛住多少用户同时访问&…

作者头像 李华
网站建设 2026/7/21 5:07:47

接口芯片技术解析:协议转换与高速数据传输

1. 接口芯片概述&#xff1a;数字世界的桥梁工程师在现代电子系统中&#xff0c;接口芯片扮演着关键的中介角色&#xff0c;如同城市交通枢纽中的调度中心。它们负责在不同协议、不同速度的设备间建立可靠的数据通道&#xff0c;解决电子元件之间的"语言障碍"问题。从…

作者头像 李华