给定总和 K 的最长公共子序列的长度
给定两个数组a[]和b[]以及一个整数K ,任务是找到最长公共子序列的长度,使得元素之和等于K 。
例子:
Input: a[] = { 9, 11, 2, 1, 6, 2, 7}, b[] = {1, 2, 6, 9, 2, 3, 11, 7}, K = 18
Output: 3
Explanation: Subsequence { 11, 7 } and { 9, 2, 7 } has sum equal to 18.
Among them { 9, 2, 7 } is longest. Therefore the output will be 3.
Input: a[] = { 2, 5, 2, 5, 7, 9, 4, 2}, b[] = { 1, 6, 2, 7, 8 }, K = 8
Output: -1
方法:解决方案的方法基于最长公共子序列的概念,我们需要检查子序列的元素之和是否等于给定值。请按照以下步骤操作;
- 考虑变量sum初始化为给定值。
- 每次当元素包含在子序列中时,减少该元素的总和值。
- 在基本条件中检查总和值是否为 0,这意味着该子序列的总和等于K。因此当sum为零时返回 0,否则返回 INT_MIN
以下是上述方法的实现:
C++
// C++ code to implement the approach
#include
using namespace std;
int solve(int a[], int b[], int i, int j, int sum)
{
if (sum == 0)
return 0;
if (sum < 0)
return INT_MIN;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return INT_MIN;
}
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return max(
1 + solve(a, b, i - 1, j - 1, sum - a[i - 1]),
solve(a, b, i - 1, j - 1, sum));
return max(solve(a, b, i - 1, j, sum),
solve(a, b, i, j - 1, sum));
}
// Driver code
int main()
{
int a[] = { 9, 11, 2, 1, 6, 2, 7 };
int b[] = { 1, 2, 6, 9, 2, 3, 11, 7 };
int n = sizeof(a) / sizeof(int);
int m = sizeof(b) / sizeof(int);
int sum = 18;
int ans = solve(a, b, n, m, sum);
if (ans >= 0)
cout << ans << endl;
else
cout << -1;
return 0;
}
Java
// Java code to implement the approach
import java.io.*;
class GFG {
static int solve(int a[], int b[], int i, int j, int sum)
{
if (sum == 0)
return 0;
if (sum < 0)
return Integer.MIN_VALUE;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return Integer.MIN_VALUE;
}
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return Math.max(
1 + solve(a, b, i - 1, j - 1, sum - a[i - 1]),
solve(a, b, i - 1, j - 1, sum));
return Math.max(solve(a, b, i - 1, j, sum),
solve(a, b, i, j - 1, sum));
}
// Driver code
public static void main (String[] args) {
int a[] = { 9, 11, 2, 1, 6, 2, 7 };
int b[] = { 1, 2, 6, 9, 2, 3, 11, 7 };
int n = a.length;
int m = b.length;
int sum = 18;
int ans = solve(a, b, n, m, sum);
if (ans >= 0)
System.out.print(ans);
else
System.out.print(-1);
}
}
// This code is contributed by hrithikgarg03188.
Python3
# Python code for the above approach
def solve(a, b, i, j, sum):
if sum == 0:
return 0
if sum < 0:
return -2147483648
if i == 0 or j == 0:
if sum == 0:
return 0
else:
return -2147483648
# If values are same then we can include this
# or also can't include this
if (a[i - 1] == b[j - 1]):
return max(
1 + solve(a, b, i - 1, j - 1, sum - a[i - 1]),
solve(a, b, i - 1, j - 1, sum))
return max(solve(a, b, i - 1, j, sum),
solve(a, b, i, j - 1, sum))
# Driver code
a = [9, 11, 2, 1, 6, 2, 7]
b = [1, 2, 6, 9, 2, 3, 11, 7]
n = len(a)
m = len(b)
sum = 18
ans = solve(a, b, n, m, sum)
if (ans >= 0):
print(ans)
else:
print(-1)
# This code is contributed by Potta Lokesh
C#
// C# code to implement the approach
using System;
class GFG {
static int solve(int[] a, int[] b, int i, int j,
int sum)
{
if (sum == 0)
return 0;
if (sum < 0)
return Int32.MinValue;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return Int32.MinValue;
}
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return Math.Max(1
+ solve(a, b, i - 1, j - 1,
sum - a[i - 1]),
solve(a, b, i - 1, j - 1, sum));
return Math.Max(solve(a, b, i - 1, j, sum),
solve(a, b, i, j - 1, sum));
}
// Driver code
public static void Main()
{
int[] a = { 9, 11, 2, 1, 6, 2, 7 };
int[] b = { 1, 2, 6, 9, 2, 3, 11, 7 };
int n = a.Length;
int m = b.Length;
int sum = 18;
int ans = solve(a, b, n, m, sum);
if (ans >= 0)
Console.Write(ans);
else
Console.Write(-1);
}
}
// This code is contributed by Samim Hossain Mondal..
Javascript
C++
// C++ code to implement the approach
#include
using namespace std;
// Function to find longest common subsequence having sum
// equal to given value
int solve(int a[], int b[], int i, int j, int sum,
map& mp)
{
if (sum == 0)
return 0;
if (sum < 0)
return INT_MIN;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return INT_MIN;
}
string temp = to_string(i) + '#'
+ to_string(j) + '#'
+ to_string(sum);
if (mp.find(temp) != mp.end())
return mp[temp];
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return mp[temp]
= max(
1 + solve(a, b, i - 1, j - 1,
sum - a[i - 1], mp),
solve(a, b, i - 1, j - 1, sum, mp));
return mp[temp]
= max(solve(a, b, i - 1, j, sum, mp),
solve(a, b, i, j - 1, sum, mp));
}
// Driver code
int main()
{
int a[] = { 9, 11, 2, 1, 6, 2, 7 };
int b[] = { 1, 2, 6, 9, 2, 3, 11, 7 };
map mp;
int n = sizeof(a) / sizeof(int);
int m = sizeof(b) / sizeof(int);
int sum = 18;
int ans = solve(a, b, n, m, sum, mp);
if (ans >= 0)
cout << ans << endl;
else
cout << -1;
return 0;
}
Java
// Java code to implement the approach
import java.util.*;
class GFG{
// Function to find longest common subsequence having sum
// equal to given value
static int solve(int a[], int b[], int i, int j, int sum,
HashMap mp)
{
if (sum == 0)
return 0;
if (sum < 0)
return Integer.MIN_VALUE;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return Integer.MIN_VALUE;
}
String temp = String.valueOf(i) + '#'
+ String.valueOf(j) + '#'
+ String.valueOf(sum);
if (mp.containsKey(temp))
return mp.get(temp);
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1]) {
mp.put(temp, Math.max(
1 + solve(a, b, i - 1, j - 1,
sum - a[i - 1], mp),
solve(a, b, i - 1, j - 1, sum, mp)));
return mp.get(temp);
}
mp.put(temp, Math.max(solve(a, b, i - 1, j, sum, mp),
solve(a, b, i, j - 1, sum, mp)));
return mp.get(temp);
}
// Driver code
public static void main(String[] args)
{
int a[] = { 9, 11, 2, 1, 6, 2, 7 };
int b[] = { 1, 2, 6, 9, 2, 3, 11, 7 };
HashMap mp = new HashMap<>();
int n = a.length;
int m = b.length;
int sum = 18;
int ans = solve(a, b, n, m, sum, mp);
if (ans >= 0)
System.out.print(ans +"\n");
else
System.out.print(-1);
}
}
// This code is contributed by shikhasingrajput
C#
// C# code to implement the approach
using System;
using System.Collections.Generic;
class GFG {
// Function to find longest common subsequence having
// sum equal to given value
static int solve(int[] a, int[] b, int i, int j,
int sum, Dictionary mp)
{
if (sum == 0)
return 0;
if (sum < 0)
return Int32.MinValue;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return Int32.MinValue;
}
string temp = i.ToString() + "#" + j.ToString()
+ "#" + sum.ToString();
if (mp.ContainsKey(temp))
return mp[temp];
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return mp[temp] = Math.Max(
1
+ solve(a, b, i - 1, j - 1,
sum - a[i - 1], mp),
solve(a, b, i - 1, j - 1, sum, mp));
return mp[temp]
= Math.Max(solve(a, b, i - 1, j, sum, mp),
solve(a, b, i, j - 1, sum, mp));
}
// Driver code
public static void Main()
{
int[] a = { 9, 11, 2, 1, 6, 2, 7 };
int[] b = { 1, 2, 6, 9, 2, 3, 11, 7 };
Dictionary mp
= new Dictionary();
int n = a.Length;
int m = b.Length;
int sum = 18;
int ans = solve(a, b, n, m, sum, mp);
if (ans >= 0)
Console.WriteLine(ans);
else
Console.Write(-1);
}
}
// This code is contributed by Samim Hossain Mondal.
输出
3
时间复杂度: O(2 N ),两个数组中的 N 最大大小
辅助空间: O(1)
有效的方法:一种有效的方法是使用记忆来降低时间复杂度,其中每个状态存储具有和的子序列的最大长度。使用地图来实现这一点。
下面是上述方法的实现。
C++
// C++ code to implement the approach
#include
using namespace std;
// Function to find longest common subsequence having sum
// equal to given value
int solve(int a[], int b[], int i, int j, int sum,
map& mp)
{
if (sum == 0)
return 0;
if (sum < 0)
return INT_MIN;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return INT_MIN;
}
string temp = to_string(i) + '#'
+ to_string(j) + '#'
+ to_string(sum);
if (mp.find(temp) != mp.end())
return mp[temp];
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return mp[temp]
= max(
1 + solve(a, b, i - 1, j - 1,
sum - a[i - 1], mp),
solve(a, b, i - 1, j - 1, sum, mp));
return mp[temp]
= max(solve(a, b, i - 1, j, sum, mp),
solve(a, b, i, j - 1, sum, mp));
}
// Driver code
int main()
{
int a[] = { 9, 11, 2, 1, 6, 2, 7 };
int b[] = { 1, 2, 6, 9, 2, 3, 11, 7 };
map mp;
int n = sizeof(a) / sizeof(int);
int m = sizeof(b) / sizeof(int);
int sum = 18;
int ans = solve(a, b, n, m, sum, mp);
if (ans >= 0)
cout << ans << endl;
else
cout << -1;
return 0;
}
Java
// Java code to implement the approach
import java.util.*;
class GFG{
// Function to find longest common subsequence having sum
// equal to given value
static int solve(int a[], int b[], int i, int j, int sum,
HashMap mp)
{
if (sum == 0)
return 0;
if (sum < 0)
return Integer.MIN_VALUE;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return Integer.MIN_VALUE;
}
String temp = String.valueOf(i) + '#'
+ String.valueOf(j) + '#'
+ String.valueOf(sum);
if (mp.containsKey(temp))
return mp.get(temp);
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1]) {
mp.put(temp, Math.max(
1 + solve(a, b, i - 1, j - 1,
sum - a[i - 1], mp),
solve(a, b, i - 1, j - 1, sum, mp)));
return mp.get(temp);
}
mp.put(temp, Math.max(solve(a, b, i - 1, j, sum, mp),
solve(a, b, i, j - 1, sum, mp)));
return mp.get(temp);
}
// Driver code
public static void main(String[] args)
{
int a[] = { 9, 11, 2, 1, 6, 2, 7 };
int b[] = { 1, 2, 6, 9, 2, 3, 11, 7 };
HashMap mp = new HashMap<>();
int n = a.length;
int m = b.length;
int sum = 18;
int ans = solve(a, b, n, m, sum, mp);
if (ans >= 0)
System.out.print(ans +"\n");
else
System.out.print(-1);
}
}
// This code is contributed by shikhasingrajput
C#
// C# code to implement the approach
using System;
using System.Collections.Generic;
class GFG {
// Function to find longest common subsequence having
// sum equal to given value
static int solve(int[] a, int[] b, int i, int j,
int sum, Dictionary mp)
{
if (sum == 0)
return 0;
if (sum < 0)
return Int32.MinValue;
if (i == 0 || j == 0) {
if (sum == 0)
return 0;
else
return Int32.MinValue;
}
string temp = i.ToString() + "#" + j.ToString()
+ "#" + sum.ToString();
if (mp.ContainsKey(temp))
return mp[temp];
// If values are same then we can include this
// or also can't include this
if (a[i - 1] == b[j - 1])
return mp[temp] = Math.Max(
1
+ solve(a, b, i - 1, j - 1,
sum - a[i - 1], mp),
solve(a, b, i - 1, j - 1, sum, mp));
return mp[temp]
= Math.Max(solve(a, b, i - 1, j, sum, mp),
solve(a, b, i, j - 1, sum, mp));
}
// Driver code
public static void Main()
{
int[] a = { 9, 11, 2, 1, 6, 2, 7 };
int[] b = { 1, 2, 6, 9, 2, 3, 11, 7 };
Dictionary mp
= new Dictionary();
int n = a.Length;
int m = b.Length;
int sum = 18;
int ans = solve(a, b, n, m, sum, mp);
if (ans >= 0)
Console.WriteLine(ans);
else
Console.Write(-1);
}
}
// This code is contributed by Samim Hossain Mondal.
输出
3
时间复杂度: O(N*M)
辅助空间: O(N * M)