求数组 B[] 的每个元素的 GCD 添加到数组 A[] 的所有元素中
给定两个数组a[]和b[] 长度分别为n和m ,任务是找到{a[0] + b[i], a[1] + b[i], a[2] + b[i] 的最大公约数(GCD) , …,a[n – 1] + b[i]} (其中 0 <= i <= m – 1)。
Input: a[] = {1, 10, 22, 64}, b[] = {5, 23, 14, 13}
Output: 3 3 3 1
Explanation:
- i = 1 : GCD(5+1, 5+10, 5+22, 5+64) = GCD(6, 15, 27, 69) = 3
- i = 2 : GCD(23+1, 23+10, 23+22, 23+64) = GCD(24, 33, 45, 87) = 3
- i = 3 : GCD(14+1, 14+10, 14+22, 14+64) = GCD(15, 24, 36, 78) = 3
- i = 4 : GCD(13+1, 13+10, 13+22, 13+64) = GCD(14, 23, 35, 77) = 1
Input: a[] = {12, 30}, b[] = {5, 23, 14, 13}
Output: 1 1 2 1
方法:可以使用欧几里得 GCD 算法的性质有效地解决该问题,该性质规定GCD(x, y) = GCD(x−y, y) 。这同样适用于多个参数GCD(x, y, z, ...) = GCD(x−y. y, z, ...) 。应用此属性,可以使用以下步骤解决问题:
- 要计算GCD(a[0] + b[i], ..., a[n – 1] + b[i]) ,请从所有其他参数中减去a[0] + b[i] 。
- 现在, GCD ( a[0] + b[i], ..., a[n – 1] + b[i]) = GCD ( a[0] + b[i], a[1] - a[0] , ..., a[n – 1] - a[0]) 。
- 求G = GCD(a[1] − a[0], ..., a[n – 1] − a[0]) ,则任何i的 gcd 可以计算为GCD(a[0] + b[i ],G) 。
- 从1到m迭代i的每个可能值,并计算 gcd 为G(i) = GCD(a[1]+b[i], G),然后打印G(i)。
下面是上述方法的实现。
C++
// C++ program for above approach
#include
using namespace std;
#define ll long long
// Function to calculate gcd for every i
void findGCDs(vector a, vector b)
{
ll g = 0;
int n = a.size();
int m = b.size();
// Update GCD of a[1] - a[0],
// a[2] - a[0], .... a[n - 1] - a[0]
for (int i = 1; i < n; i++) {
g = __gcd(g, a[i] - a[0]);
}
// Print gcd(g, a[0] + b[j])
for (int j = 0; j < m; j++) {
cout << __gcd(g, a[0] + b[j]) << " ";
}
}
// Driver Code
int main()
{
// Given Input
vector a = { 1, 10, 22, 64 },
b = { 5, 23, 14, 13 };
// Function Call
findGCDs(a, b);
return 0;
}
Java
// Java code for the above approach
public class GFG{
static int gcd(int a, int b)
{
if (b == 0)
return a;
return gcd(b, a % b);
}
// Function to calculate gcd for every i
static void findGCDs(int[] a, int[] b)
{
int g = 0;
int n = a.length;
int m = b.length;
// Update GCD of a[1] - a[0],
// a[2] - a[0], .... a[n - 1] - a[0]
for (int i = 1; i < n; i++) {
g = gcd(g, a[i] - a[0]);
}
// Print gcd(g, a[0] + b[j])
for (int j = 0; j < m; j++) {
System.out.print(gcd(g, a[0] + b[j]) + " ");
}
}
// Driver Code
public static void main(String args[])
{
// Given Input
int[] a = { 1, 10, 22, 64 },
b = { 5, 23, 14, 13 };
// Function Call
findGCDs(a, b);
}
}
// This code is contributed by SoumikMondal.
Python3
# Python program for above approach
import math
# Function to calculate gcd for every i
def findGCDs( a, b):
g = 0
n = len(a)
m = len(b)
# Update GCD of a[1] - a[0],
# a[2] - a[0], .... a[n - 1] - a[0]
for i in range(1,n):
g = math.gcd(g, a[i] - a[0])
# Pr gcd(g, a[0] + b[j])
for j in range(m):
print(math.gcd(g, a[0] + b[j]), end=" ")
# Driver Code
# Given Input
a = [1, 10, 22, 64]
b = [5, 23, 14, 13]
# Function Call
findGCDs(a, b)
#This code is contributed by shubhamsingh10
C#
//C# code for the above approach
using System;
public class GFG{
static int gcd(int a, int b)
{
if (b == 0)
return a;
return gcd(b, a % b);
}
// Function to calculate gcd for every i
static void findGCDs(int[] a, int[] b)
{
int g = 0;
int n = a.Length;
int m = b.Length;
// Update GCD of a[1] - a[0],
// a[2] - a[0], .... a[n - 1] - a[0]
for (int i = 1; i < n; i++) {
g = gcd(g, a[i] - a[0]);
}
// Print gcd(g, a[0] + b[j])
for (int j = 0; j < m; j++) {
Console.Write(gcd(g, a[0] + b[j]) + " ");
}
}
// Driver Code
static public void Main ()
{
// Given Input
int[] a = { 1, 10, 22, 64 },
b = { 5, 23, 14, 13 };
// Function Call
findGCDs(a, b);
}
}
// This code is contributed by shubhamsingh10.
Javascript
输出:
3 3 3 1
时间复杂度: O((N + M) * log(X)),其中M是数组a[]中的最大元素。
辅助空间: O(1)