您的位置:首页 > 房产 > 家装 > 济南互联网公司有哪些_正规免费发布信息平台_新的seo网站优化排名 排名_广州网络营销运营

济南互联网公司有哪些_正规免费发布信息平台_新的seo网站优化排名 排名_广州网络营销运营

2025/1/5 6:57:45 来源:https://blog.csdn.net/weixin_43724673/article/details/142746992  浏览:    关键词:济南互联网公司有哪些_正规免费发布信息平台_新的seo网站优化排名 排名_广州网络营销运营
济南互联网公司有哪些_正规免费发布信息平台_新的seo网站优化排名 排名_广州网络营销运营

0-1 背包问题 二维

题目链接/文章讲解:代码随想录
视频讲解:带你学透 0-1 背包问题!| 关于背包问题,你不清楚的地方,这里都讲了!| 动态规划经典问题 | 数据结构与算法_哔哩哔哩_bilibili

import java.util.Scanner;public class Main1 {public static void main(String[] args) {Scanner sc = new Scanner(System.in);int n = sc.nextInt(); // 物品数量int bagweight = sc.nextInt(); // 背包容量int[] weight = new int[n];int[] value = new int[n];// 输入物品的重量for (int i = 0; i < n; i++) {weight[i] = sc.nextInt();}// 输入物品的价值for (int i = 0; i < n; i++) {value[i] = sc.nextInt();}// 动态规划数组int[][] dp = new int[n][bagweight + 1];// 初始化第一个物品for (int j = weight[0]; j <= bagweight; j++) {dp[0][j] = value[0];}// 填充动态规划表for (int i = 1; i < n; i++) {for (int j = 0; j <= bagweight; j++) {if (j < weight[i]) {// 当前物品的重量大于当前背包容量dp[i][j] = dp[i - 1][j]; // 不放当前物品} else {// 当前物品可以放入背包dp[i][j] = Math.max(dp[i - 1][j], dp[i - 1][j - weight[i]] + value[i]);}}}// 输出结果System.out.println(dp[n - 1][bagweight]);}
}

0-1 背包问题 一维

题目链接/文章讲解:代码随想录
视频讲解:带你学透 01 背包问题(滚动数组篇) | 从此对背包问题不再迷茫!_哔哩哔哩_bilibili

import java.util.Scanner;public class Main {public static void main(String[] args) {Scanner sc = new Scanner(System.in);int n = sc.nextInt(); // 物品数量int bagweight = sc.nextInt(); // 背包容量int[] weight = new int[n];int[] value = new int[n];// 输入物品的重量for (int i = 0; i < n; i++) {weight[i] = sc.nextInt();}// 输入物品的价值for (int i = 0; i < n; i++) {value[i] = sc.nextInt();}// 使用一维数组进行动态规划int[] dp = new int[bagweight + 1];// 填充动态规划数组for (int i = 0; i < n; i++) {for (int j = bagweight; j >= weight[i]; j--) {dp[j] = Math.max(dp[j], dp[j - weight[i]] + value[i]);}}// 输出结果System.out.println(dp[bagweight]);}
}

416. 分割等和子集

题目链接/文章讲解:代码随想录
视频讲解:动态规划之背包问题,这个包能装满吗?| LeetCode:416.分割等和子集_哔哩哔哩_bilibili

class Solution {public boolean canPartition(int[] nums) {int sum = 0;for (int num : nums) {sum += num;}// 如果总和是奇数,无法分成两个相等的子集if (sum % 2 != 0) {return false;}int target = sum / 2;int n = nums.length;// 创建一个 dp 数组,表示是否可以达到特定的和boolean[][] dp = new boolean[n + 1][target + 1];// 初始化:可以达到和为 0for (int i = 0; i <= n; i++) {dp[i][0] = true;}// 填充 dp 数组for (int i = 1; i <= n; i++) {for (int j = 0; j <= target; j++) {if (j < nums[i - 1]) {// 当前数字大于目标和,无法选择它dp[i][j] = dp[i - 1][j];} else {// 选择当前数字或不选择它dp[i][j] = dp[i - 1][j] || dp[i - 1][j - nums[i - 1]];}}}// 返回能否达到 targetreturn dp[n][target];}
}

代码解释

  1. 计算总和: 首先通过一个循环计算 nums 数组的总和 sum

  2. 检查奇偶性: 如果 sum 是奇数,则不可能将数组分成两个相等的子集,直接返回 false

  3. 动态规划数组: 创建一个二维布尔数组 dp,其中 dp[i][j] 表示前 i 个数字是否可以组成和为 j 的子集。

  4. 初始化:

    • 任何情况下,和为 0 只需要不选择任何数字,因此 dp[i][0] 都是 true
  5. 填充 dp 数组:

    • 通过两层循环遍历每个数字和每个可能的和。如果当前数字大于目标和 j,则无法选择它,dp[i][j] 等于不选择它的结果 dp[i-1][j]
    • 如果可以选择当前数字,则 dp[i][j] 等于选择当前数字或不选择它的结果,即 dp[i][j] = dp[i-1][j] || dp[i-1][j - nums[i - 1]]
  6. 返回结果: 最后返回 dp[n][target],表示是否可以用前 n 个数字组成和为 target 的子集。

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com