news 2026/6/12 22:16:59

京东Java面试被问:动态规划的状态压缩和优化技巧

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
京东Java面试被问:动态规划的状态压缩和优化技巧

一、什么是状态压缩动态规划

状态压缩DP是用二进制位位运算来表示和存储状态的一类DP,主要用于解决状态维度高但每个维度状态数少的问题(通常是布尔值)。

典型特征:

  • 状态中的每一维只有少量可能值(通常是0/1)

  • 状态空间巨大但可压缩

  • 常与排列、选择、覆盖等问题相关

二、状态压缩的核心技巧

1.二进制位表示法

python

复制

下载

# 用整数mask的二进制位表示选择状态 mask = 0b10101 # 表示第0、2、4个元素被选中 n = 5 for i in range(n): if mask & (1 << i): # 检查第i位是否为1 print(f"元素{i}被选中")

2.常见位运算操作

python

复制

下载

# 基本操作 S = (1 << n) - 1 # n位全1 S & (1 << i) # 判断第i位是否为1 S | (1 << i) # 设置第i位为1 S & ~(1 << i) # 设置第i位为0 S ^ (1 << i) # 翻转第i位 S & (S - 1) # 清除最低位的1

三、经典问题模型

1.旅行商问题(TSP)

python

复制

下载

def tsp(n, dist): # dp[mask][i]: 访问过mask中的城市,最后在i城市的最小代价 dp = [[float('inf')] * n for _ in range(1 << n)] dp[1][0] = 0 # 从城市0开始 for mask in range(1 << n): for i in range(n): if not (mask & (1 << i)): continue for j in range(n): if mask & (1 << j): continue new_mask = mask | (1 << j) dp[new_mask][j] = min(dp[new_mask][j], dp[mask][i] + dist[i][j]) # 返回起点并形成环路 return min(dp[(1 << n) - 1][i] + dist[i][0] for i in range(1, n))

2.棋盘覆盖问题

python

复制

下载

def domino_cover(n, m): # dp[i][mask]: 处理到第i行,当前行状态为mask dp = [0] * (1 << m) dp[(1 << m) - 1] = 1 # 初始状态 for i in range(n): new_dp = [0] * (1 << m) for mask in range(1 << m): if dp[mask] == 0: continue # 递归填充当前行 def dfs(col, current_mask, next_mask): if col == m: new_dp[next_mask] += dp[mask] return # 如果当前位置已被覆盖 if mask & (1 << col): dfs(col + 1, current_mask, next_mask) else: # 竖放 if i < n - 1: dfs(col + 1, current_mask | (1 << col), next_mask | (1 << col)) # 横放 if col < m - 1 and not (mask & (1 << (col + 1))): dfs(col + 2, current_mask | (3 << col), next_mask) dfs(0, 0, 0) dp = new_dp return dp[(1 << m) - 1]

篇幅限制下面就只能给大家展示小册部分内容了。整理了一份核心面试笔记包括了:Java面试、Spring、JVM、MyBatis、Redis、MySQL、并发编程、微服务、Linux、Springboot、SpringCloud、MQ、Kafc

需要全套面试笔记及答案
【点击此处即可/免费获取】​​​

四、高级优化技巧

1.枚举子集优化

python

复制

下载

# 高效枚举mask的所有子集 def enumerate_subsets(mask): subset = mask while subset: # 处理子集subset process(subset) subset = (subset - 1) & mask # 处理空集 process(0) # 复杂度:O(3^n) 而非 O(4^n) for mask in range(1 << n): subset = mask while subset: # subset是mask的子集 complement = mask ^ subset # mask除去subset的部分 subset = (subset - 1) & mask

2.滚动数组优化

python

复制

下载

# 二维降一维 dp = [0] * (1 << n) dp[0] = 1 for i in range(m): new_dp = [0] * (1 << n) for mask in range(1 << n): if dp[mask]: # 状态转移 for new_mask in next_masks(mask): new_dp[new_mask] += dp[mask] dp = new_dp

3.预处理合法状态

python

复制

下载

# 预处理所有合法状态,减少无效转移 def preprocess_states(n): valid_states = [] for mask in range(1 << n): # 检查是否没有相邻的1 if not (mask & (mask << 1)): valid_states.append(mask) return valid_states # 预处理状态间转移 def preprocess_transitions(valid_states): transitions = {} for s1 in valid_states: transitions[s1] = [] for s2 in valid_states: if not (s1 & s2): # 状态兼容性检查 transitions[s1].append(s2) return transitions

4.Meet-in-the-Middle

python

复制

下载

def meet_in_middle(n, target): half = n // 2 left_sums = {} # 枚举前半部分 for mask in range(1 << half): s = sum(nums[i] for i in range(half) if mask & (1 << i)) left_sums[s] = left_sums.get(s, 0) + 1 # 枚举后半部分 result = 0 for mask in range(1 << (n - half)): s = sum(nums[half + i] for i in range(n - half) if mask & (1 << i)) if target - s in left_sums: result += left_sums[target - s] return result

篇幅限制下面就只能给大家展示小册部分内容了。整理了一份核心面试笔记包括了:Java面试、Spring、JVM、MyBatis、Redis、MySQL、并发编程、微服务、Linux、Springboot、SpringCloud、MQ、Kafc

需要全套面试笔记及答案
【点击此处即可/免费获取】​​​

五、实战技巧总结

1.空间优化优先级

text

复制

下载

位运算压缩 → 滚动数组 → 按块处理 → 状态哈希

2.时间优化策略

  • 预处理合法状态和转移

  • 使用位运算加速状态检查

  • 剪枝无效状态

  • 使用对称性减少状态数

3.常见易错点

python

复制

下载

# 错误:忘记处理空集 subset = mask while True: # 这样会跳过空集 # ... if subset == 0: break subset = (subset - 1) & mask # 正确:显式处理空集 subset = mask while subset: # ... subset = (subset - 1) & mask # 处理空集 process(0)

六、复杂度分析

问题类型状态数常见复杂度优化目标
普通状态压缩O(2^n)O(2^n * n)减少n或优化转移
带约束压缩O(有效状态)O(状态数²)预处理合法状态
多维压缩O(2^(n*m))指数级Meet-in-Middle

七、练习题推荐

  1. 入门:LeetCode 78(子集)、LeetCode 526(优美的排列)

  2. 中等:LeetCode 464(我能赢吗)、LeetCode 691(贴纸拼词)

  3. 进阶:LeetCode 1434(每个人戴不同帽子的方案数)

  4. 竞赛级:POJ 2411(铺砖)、UVa 11825(黑客攻击)

八、最佳实践建议

  1. 先写朴素DP,再压缩:确保逻辑正确后再优化

  2. 状态设计要简洁:能用1位不用2位

  3. 善用位运算函数:提高代码可读性

  4. 注意位序方向:统一从低位到高位或反之

  5. 测试边界情况:空集、全集、最大规模

掌握状态压缩的关键在于多练习、多总结。从经典的TSP和铺砖问题开始,逐步扩展到更复杂的问题,你会逐渐建立状态设计的直觉。记住:好的状态设计能让复杂问题变得简单,而差的设计会让简单问题变得复杂。

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

Nodejs和vue框架的医疗设备维护平台_医院设备维修系统-- 项目源码

文章目录Node.js与Vue医疗设备维护平台项目摘要--nodejs技术栈--结论源码文档获取/同行可拿货,招校园代理 &#xff1a;文章底部获取博主联系方式&#xff01;Node.js与Vue医疗设备维护平台项目摘要 该医疗设备维护平台基于Node.js后端与Vue.js前端构建&#xff0c;专为医院设…

作者头像 李华
网站建设 2026/6/4 0:11:30

【无人机三维路径规划】基于鳄鱼伏击算法CAOA多无人机协同集群避障路径规划(目标函数:最低成本:路径、高度、威胁、转角)附Matlab代码

✅作者简介&#xff1a;热爱科研的Matlab仿真开发者&#xff0c;擅长数据处理、建模仿真、程序设计、完整代码获取、论文复现及科研仿真。 &#x1f34e; 往期回顾关注个人主页&#xff1a;Matlab科研工作室 &#x1f447; 关注我领取海量matlab电子书和数学建模资料 &#x1…

作者头像 李华
网站建设 2026/5/31 0:41:17

2026年1月亲测:那些超实用PPT模板分享

2026年1月亲测&#xff1a;那些超实用PPT模板分享行业痛点分析当前PPT模板领域面临着诸多技术挑战。首先&#xff0c;模板的多样性和适用性不足&#xff0c;许多模板难以满足不同行业和场景的需求。其次&#xff0c;模板的质量参差不齐&#xff0c;一些模板在设计上缺乏专业性和…

作者头像 李华
网站建设 2026/6/10 13:26:31

校园二手闲置物品租售系统_

文章目录校园二手闲置物品租售系统的摘要--nodejs技术栈--结论源码文档获取/同行可拿货,招校园代理 &#xff1a;文章底部获取博主联系方式&#xff01;校园二手闲置物品租售系统的摘要 校园二手闲置物品租售系统是一种基于互联网平台的交易解决方案&#xff0c;旨在优化校园内…

作者头像 李华
网站建设 2026/6/7 17:49:01

社区闲置物品交易求购系统

文章目录社区闲置物品交易求购系统摘要--nodejs技术栈--结论源码文档获取/同行可拿货,招校园代理 &#xff1a;文章底部获取博主联系方式&#xff01;社区闲置物品交易求购系统摘要 社区闲置物品交易求购系统旨在通过数字化平台解决居民闲置物品处理需求&#xff0c;促进资源循…

作者头像 李华