【动态规划】Subarray Sum Equals K-子数组和为K

版权声明:本文为博主原创文章,欢迎大家转载,但是要注明我的文章地址。 https://blog.csdn.net/program_developer/article/details/83625544

题目描述:

给定一个整数数组和一个整数 k,你需要找到该数组中和为 k 的子数组。如果存在该子数组返回true,否则返回false。

输入输出:

input:{3, 34, 4, 12,5, 2}

output:true

 解题思路:

(1)最优子结构

(2)状态转移方程

(3)边界条件

情况1:如果s=0时,直接返回true。

情况2:当指针到数组下标为0的时候,判断arr[0]是否等于s。

情况3: 当arr[i] 大于s时,我们就不考虑选arr[i]的情况,只考虑不选arr[i]的情况。

代码实现:

(1)递归方法

public class subArrayEqualsK {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int[] arr = {3, 34, 4, 12, 5, 2};
		System.out.println(rec_subSet(arr, arr.length-1, 9));
	}
	
	/**
	 * 递归方法
	 * @param arr
	 * @param i
	 * @param s
	 * @return
	 */
	public static boolean rec_subSet(int[] arr,int i, int s) {
		if(s == 0)
			return true;
		else if(i == 0) {
			if(arr[i] == s)
				return true;
			else
				return false;
		}
		else if(arr[i] > s) {
			return rec_subSet(arr, i-1, s);
		}
		else {
			boolean a = rec_subSet(arr, i-1, s-arr[i]);
			boolean b = rec_subSet(arr, i-1, s);
			if(a || b)
				return true;
			else 
				return false;
		}
	}
}

(2)动态规划方法

public class subArrayEqualsK {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int[] arr = {3, 34, 4, 12, 5, 2};
		System.out.println(dp_subSet(arr, 9));
		System.out.println(dp_subSet(arr, 10));
		System.out.println(dp_subSet(arr, 11));
		System.out.println(dp_subSet(arr, 12));
		System.out.println(dp_subSet(arr, 13));
	}
	
	/**
	 * 动态规划解法
	 * @param arr
	 * @param s
	 * @return
	 */
	public static boolean dp_subSet(int[] arr, int s) {
		// 构建状态数组
		boolean[][] subSet = new boolean[arr.length][s+1];
		for(int i=0; i<arr.length; i++) {
			subSet[i][0] = true;
		}
		for(int i=0; i<s+1; i++) {
			subSet[0][i] = false;
		}
		subSet[0][arr[0]] = true;
		// 在根据状态方程,填充状态数组
		for(int i=1; i<arr.length; i++) {
			for(int j=1; j<s+1; j++) {
				if(arr[i] > j)
					subSet[i][j] = subSet[i-1][j];
				else {
					boolean A = subSet[i-1][j-arr[i]];
					boolean B = subSet[i-1][j];
					if(A || B)
						subSet[i][j] = true;
					else 
						subSet[i][j] = false;
				}
			}
		}
		return subSet[arr.length-1][s];
	}
}

Reference:

【1】https://www.bilibili.com/video/av18512769/?spm_id_from=333.788.videocard.0

猜你喜欢

转载自blog.csdn.net/program_developer/article/details/83625544