📜  任意一对不同元素之间具有最大GCD的最长子序列

📅  最后修改于: 2021-05-14 07:55:37             🧑  作者: Mango

给定的阵列ARR []N个正整数,任务是从给定的阵列,使得所述亚序列中的任何两个不同整数的GCD是最大找到子序列的最大长度。

例子:

天真的方法:最简单的方法是使用递归并递归生成给定数组的所有可能子序列,并在这些子序列中找到最大长度。步骤如下:

  • 创建一个函数以使用Eratosthenes筛子的思想在数组中找到具有最大GCD (例如maxGCD )的对。
  • 创建另一个函数以计算任意两个不同元素之间的GCD最大的子序列数组的最大长度:
    • 创建一个辅助数组arr1 [] ,该数组以排序顺序存储数组元素。
    • 将两个变量初始化为[0,0]并递归生成所有子序列,并返回GCD为maxGCD的子序列的最大长度。
  • 完成上述步骤后,通过上述递归调用打印返回的最大长度。

 下面是上述方法的实现:

C++
// C++ program for the above approach
#include
using namespace std;
 
// Function to find GCD of pair with
// maximum GCD
int findMaxGCD(int arr[], int N)
{
     
    // Stores maximum element of arr[]
    int high = 0;
     
    // Find the maximum element
    for(int i = 0; i < N; i++)
    {
        high = max(high, arr[i]);
    }
 
    // Maintain a count array
    int count[high + 1] = {0};
     
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
    {
        count[arr[i]] += 1;
    }
 
    // Stores the multiples of a number
    int counter = 0;
 
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
        int j = i;
 
        // Iterate from current potential
        // GCD till it is less than MAX
        while (j <= high)
        {
             
            // A multiple found
            if (count[j] > 0)
                counter += count[j];
 
            // Increment potential GCD by
            // itself io check i, 2i, 3i...
            j += i;
 
            // If 2 multiples found max
            // GCD found
            if (counter == 2)
                return i;
        }
        counter = 0;
    }
}
     
// Function to find longest subsequence
// such that GCD of any two distinct
// integers is maximum
int maxlen(int i, int j, int arr[],
           int arr1[], int N, int maxgcd)
{
    int a = 1;
 
    // Base Cases
    if (i >= N or j >= N)
        return 0;
 
    // Comapare current GCD to the
    // maximum GCD
    if (__gcd(arr[i], arr1[j]) == maxgcd &&
              arr[i] != arr1[j])
    {
         
        // If true increment and
        // move the pointer
        a = max(a, 1 + maxlen(i, j + 1,
                              arr, arr1,
                              N, maxgcd));
        return a;
    }
     
    // Return max of either subsequences
    return max(maxlen(i + 1, j, arr,
                      arr1, N, maxgcd),
               maxlen(i, j + 1, arr,
                      arr1, N, maxgcd));
}
 
// Driver Code
int main()
{
    int arr[] = { 1, 2, 8, 5, 6 };
    int arr1[] = { 1, 2, 8, 5, 6 };
     
    // Sorted array
    int n = sizeof(arr) / sizeof(arr[0]);
     
    sort(arr, arr + n);
    sort(arr1, arr1 + n);
     
    // Function call to calculate GCD of
    // pair with maximum GCD
    int maxgcd = findMaxGCD(arr, n);
     
    // Print the result
    cout << maxlen(0, 0, arr,
                   arr1, n, maxgcd) + 1;
}
 
// This code is contributed by ipg2016107


Java
// Java program for the
// above approach
import java.util.*;
 
class GFG{
     
// Recursive function to
// return gcd of a and b 
static int __gcd(int a,
                 int b) 
{ 
  return b == 0 ?
         a :__gcd(b, a % b);    
}
   
// Function to find GCD of
// pair with maximum GCD
static int findMaxGCD(int arr[],
                      int N)
{   
  // Stores maximum element
  // of arr[]
  int high = 0;
 
  // Find the maximum element
  for(int i = 0; i < N; i++)
  {
    high = Math.max(high,
                    arr[i]);
  }
 
  // Maintain a count array
  int []count = new int[high + 1];
 
  // Store the frequency of arr[]
  for(int i = 0; i < N; i++)
  {
    count[arr[i]] += 1;
  }
 
  // Stores the multiples of
  // a number
  int counter = 0;
 
  // Iterate over the  range
  // [MAX, 1]
  for(int i = high; i > 0; i--)
  {
    int j = i;
 
    // Iterate from current potential
    // GCD till it is less than MAX
    while (j <= high)
    {
      // A multiple found
      if (count[j] > 0)
        counter += count[j];
 
      // Increment potential GCD by
      // itself io check i, 2i, 3i...
      j += i;
 
      // If 2 multiples found max
      // GCD found
      if (counter == 2)
        return i;
    }
    counter = 0;
  }
  return 0;
}
 
// Function to find longest
// subsequence such that GCD
// of any two distinct integers
// is maximum
static int maxlen(int i, int j,
                  int arr[],
                  int arr1[],
                  int N, int maxgcd)
{
  int a = 1;
 
  // Base Cases
  if (i >= N || j >= N)
    return 0;
 
  // Comapare current GCD to
  // the maximum GCD
  if (__gcd(arr[i], arr1[j]) == maxgcd &&
      arr[i] != arr1[j])
  {
    // If true increment and
    // move the pointer
    a = Math.max(a, 1 + maxlen(i, j + 1,
                               arr, arr1,
                               N, maxgcd));
    return a;
  }
 
  // Return max of either subsequences
  return Math.max(maxlen(i + 1, j, arr,
                         arr1, N, maxgcd),
                  maxlen(i, j + 1, arr,
                         arr1, N, maxgcd));
}
 
// Driver Code
public static void main(String[] args)
{
  int arr[] = {1, 2, 8, 5, 6};
  int arr1[] = {1, 2, 8, 5, 6};
 
  // Sorted array
  int n = arr.length;
 
  Arrays.sort(arr);
 
  // Function call to calculate GCD of
  // pair with maximum GCD
  int maxgcd = findMaxGCD(arr, n);
 
  // Print the result
  System.out.print(maxlen(0, 0, arr,
                          arr1, n, maxgcd));
}
}
 
// This code is contributed by gauravrajput1


Python3
# Python3 program for the above approach
import math
 
# Function to find GCD of pair with
# maximum GCD
def findMaxGCD(arr, N):
     
    # Stores maximum element of arr[]
    high = 0
     
    # Find the maximum element
    for i in range(0, N):
        high = max(high, arr[i])
 
    # Maintain a count array
    count = [0] * (high + 1)
     
    # Store the frequency of arr[]
    for i in range(0, N):
        count[arr[i]] += 1
 
    # Stores the multiples of a number
    counter = 0
 
    # Iterate over the  range [MAX, 1]
    for i in range(high, 0, -1):
        j = i
 
        # Iterate from current potential
        # GCD till it is less than MAX
        while (j <= high):
 
            # A multiple found
            if (count[j] > 0):
                counter += count[j]
 
            # Increment potential GCD by
            # itself io check i, 2i, 3i...
            j += i
 
            # If 2 multiples found max
            # GCD found
            if (counter == 2):
                return i
 
        counter = 0
 
# Function to find longest subsequence
# such that GCD of any two distinct
# integers is maximum
def maxlen(i, j):
    a = 0
 
    # Base Cases
    if i >= N or j >= N:
        return 0
 
    # Comapare current GCD to the
    # maximum GCD
    if math.gcd(arr[i], arr1[j]) == maxgcd and arr[i] != arr1[j]:
 
        # If true increment and
        # move the pointer
        a = max(a, 1 + maxlen(i, j + 1))
        return a
 
    # Return max of either subsequences
    return max(maxlen(i + 1, j), maxlen(i, j + 1))
 
 
# Drivers Code
arr = [1, 2, 8, 5, 6]
 
# Sorted array
arr1 = sorted(arr)
 
# Length of the array
N = len(arr)
 
# Function call to calculate GCD of
# pair with maximum GCD
maxgcd = findMaxGCD(arr, N)
 
# Print the result
print(maxlen(0, 0))


C#
// C# program for the
// above approach
using System;
 
class GFG{
     
// Recursive function to
// return gcd of a and b 
static int __gcd(int a, int b) 
{
  return b == 0 ?
         a :__gcd(b, a % b);    
}
   
// Function to find GCD of
// pair with maximum GCD
static int findMaxGCD(int []arr,
                      int N)
{   
   
  // Stores maximum element
  // of []arr
  int high = 0;
 
  // Find the maximum element
  for(int i = 0; i < N; i++)
  {
    high = Math.Max(high,
                    arr[i]);
  }
 
  // Maintain a count array
  int []count = new int[high + 1];
 
  // Store the frequency of []arr
  for(int i = 0; i < N; i++)
  {
    count[arr[i]] += 1;
  }
 
  // Stores the multiples of
  // a number
  int counter = 0;
 
  // Iterate over the  range
  // [MAX, 1]
  for(int i = high; i > 0; i--)
  {
    int j = i;
 
    // Iterate from current potential
    // GCD till it is less than MAX
    while (j <= high)
    {
       
      // A multiple found
      if (count[j] > 0)
        counter += count[j];
 
      // Increment potential GCD by
      // itself io check i, 2i, 3i...
      j += i;
 
      // If 2 multiples found max
      // GCD found
      if (counter == 2)
        return i;
    }
    counter = 0;
  }
  return 0;
}
 
// Function to find longest
// subsequence such that GCD
// of any two distinct integers
// is maximum
static int maxlen(int i, int j,
                  int []arr,
                  int []arr1,
                  int N, int maxgcd)
{
  int a = 1;
 
  // Base Cases
  if (i >= N || j >= N)
    return 0;
 
  // Comapare current GCD to
  // the maximum GCD
  if (__gcd(arr[i], arr1[j]) == maxgcd &&
                      arr[i] != arr1[j])
  {
     
    // If true increment and
    // move the pointer
    a = Math.Max(a, 1 + maxlen(i, j + 1,
                               arr, arr1,
                               N, maxgcd));
    return a;
  }
 
  // Return max of either subsequences
  return Math.Max(maxlen(i + 1, j, arr,
                         arr1, N, maxgcd),
                  maxlen(i, j + 1, arr,
                         arr1, N, maxgcd));
}
 
// Driver Code
public static void Main(String[] args)
{
  int []arr = { 1, 2, 8, 5, 6 };
  int []arr1 = { 1, 2, 8, 5, 6 };
 
  // Sorted array
  int n = arr.Length;
 
  Array.Sort(arr);
 
  // Function call to calculate GCD of
  // pair with maximum GCD
  int maxgcd = findMaxGCD(arr, n);
 
  // Print the result
  Console.Write(maxlen(0, 0, arr,
                       arr1, n, maxgcd));
}
}
 
// This code is contributed by Princi Singh


Javascript


C++
// C++ program for the above approach
#include
using namespace std;
 
map, int>dp;
int maxgcd;
vectorarr, arr1;
int N;
 
// Function to find GCD of pair with
// maximum GCD
int findMaxGCD(vectorarr, int  N)
{
     
    // Stores maximum element of arr[]
    int high = 0;
     
    // Find the maximum element
    for(int i = 0; i < N; i++)
        high = max(high, arr[i]);
         
    // Maintain a count array
    int count[high + 1] = {0};
 
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
        count[arr[i]] += 1;
         
    // Stores the multiples of a number
    int counter = 0;
     
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
        int j = i;
         
        // Iterate from current potential
        // GCD till it is less than MAX
        while (j <= high)
        {
             
            // A multiple found
            if (count[j] > 0)
                counter += count[j];
                 
            // Increment potential GCD by
            // itself io check i, 2i, 3i...
            j += i;
             
            // If 2 multiples found max
            // GCD found
            if (counter == 2)
                return i;
        }
        counter = 0;
    }
    return 1;
}
     
// Function to find longest subsequence
// such that GCD of any two distinct
// integers is maximum
int maxlen(int i, int j)
{
    int  a = 0;
 
    // Create the key
    // Base Case
    if (i >= N or j >= N)
        return 0;
         
    // Check if the current state is
    // already calculated
    if (dp[{i, j}])
        return dp[{i, j}];
       
    // Compare current GCD to the
    // maximum GCD
    if (__gcd(arr[i], arr1[j]) ==
        maxgcd && arr[i] != arr1[j])
    {
         
        // If true increment and
        // move the pointer
        dp[{i, j}] = 1 + maxlen(i, j + 1);
        return dp[{i, j}];
    }
     
    // Return max of either subsequences
    return (max(maxlen(i + 1, j),
                maxlen(i, j + 1)));
}
   
// Driver Code
int main()
{
    arr = { 1, 2, 8, 5, 6 };
    arr1 = arr;
     
    // Sorted array
    sort(arr1.begin(), arr1.end());
     
    // Length of the array
    N = arr.size();
     
    // Function Call
    maxgcd = findMaxGCD(arr, N);
     
    // Print the result
    cout << (maxlen(0, 0));
}
 
// This code is contributed by Stream_Cipher


Java
// Java program for the above approach
import java.util.*;
import java.awt.Point;
public class Main
{
  static HashMap dp = new HashMap<>();
  static int maxgcd, N;
  static Vector arr;
  static Vector arr1;
 
  static int __gcd(int a, int b)
  {
    if (b == 0)
      return a;
 
    return __gcd(b, a % b);
  }
 
  // Function to find GCD of pair with
  // maximum GCD
  static int findMaxGCD(Vector arr, int N)
  {
 
    // Stores maximum element of arr[]
    int high = 0;
 
    // Find the maximum element
    for(int i = 0; i < N; i++)
      high = Math.max(high, arr.get(i));
 
    // Maintain a count array
    int[] count = new int[high + 1];
 
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
      count[arr.get(i)] += 1;
 
    // Stores the multiples of a number
    int counter = 0;
 
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
      int j = i;
 
      // Iterate from current potential
      // GCD till it is less than MAX
      while (j <= high)
      {
 
        // A multiple found
        if (count[j] > 0)
          counter += count[j];
 
        // Increment potential GCD by
        // itself io check i, 2i, 3i...
        j += i;
 
        // If 2 multiples found max
        // GCD found
        if (counter == 2)
          return i;
      }
      counter = 0;
    }
    return 1;
  }
 
  // Function to find longest subsequence
  // such that GCD of any two distinct
  // integers is maximum
  static int maxlen(int i, int j)
  {
 
    // Create the key
    // Base Case
    if (i >= N || j >= N)
      return 0;
 
    // Check if the current state is
    // already calculated
    if (dp.containsKey(new Point(i, j)))
      return dp.get(new Point(i, j));
 
    // Compare current GCD to the
    // maximum GCD
    if (__gcd(arr.get(i), arr1.get(j)) ==
        maxgcd && arr.get(i) != arr1.get(j))
    {
 
      // If true increment and
      // move the pointer
      dp.put(new Point(i, j), 1 + maxlen(i, j + 1));
      return dp.get(new Point(i, j));
    }
 
    // Return max of either subsequences
    return (Math.max(maxlen(i + 1, j), maxlen(i, j + 1)));
  }
 
  public static void main(String[] args) {
    arr = new Vector();
    arr.add(1);
    arr.add(2);
    arr.add(8);
    arr.add(5);
    arr.add(6);
    arr1 = arr;
 
    // Sorted array
    Collections.sort(arr1);
 
    // Length of the array
    N = arr.size();
 
    // Function Call
    maxgcd = findMaxGCD(arr, N);
 
    // Print the result
    System.out.println(maxlen(0, 0) + 1);
  }
}
 
// This code is contributed by divyeshrabadiya07.


Python3
# Python3 program for the above approach
import math
 
# Function to find GCD of pair with
# maximum GCD
def findMaxGCD(arr, N):
     
    # Stores maximum element of arr[]
    high = 0
     
    # Find the maximum element
    for i in range(0, N):
        high = max(high, arr[i])
 
    # Maintain a count array
    count = [0] * (high + 1)
     
    # Store the frequency of arr[]
    for i in range(0, N):
        count[arr[i]] += 1
 
    # Stores the multiples of a number
    counter = 0
 
    # Iterate over the  range [MAX, 1]
    for i in range(high, 0, -1):
        j = i
 
        # Iterate from current potential
        # GCD till it is less than MAX
        while (j <= high):
 
            # A multiple found
            if (count[j] > 0):
                counter += count[j]
 
            # Increment potential GCD by
            # itself io check i, 2i, 3i...
            j += i
 
            # If 2 multiples found max
            # GCD found
            if (counter == 2):
                return i
 
        counter = 0
 
# Function to find longest subsequence
# such that GCD of any two distinct
# integers is maximum
def maxlen(i, j):
   
    a = 0
     
    # Create the key
    key = (i, j)
 
    # Base Case
    if i >= N or j >= N:
        return 0
     
    # Check if the current state is
    # already calculated
    if key in dp:
        return dp[key]
       
    # Comapare current GCD to the
    # maximum GCD
    if math.gcd(arr[i], arr1[j]) == maxgcd and arr[i] != arr1[j]:
 
        # If true increment and
        # move the pointer
        dp[key] = 1 + maxlen(i, j + 1)
 
        return dp[key]
 
    # Return max of either subsequences
    return max(maxlen(i + 1, j), maxlen(i, j + 1))
 
 
# Drivers code
arr = [1, 2, 8, 5, 6]
 
# Empty dictionary
dp = dict()
 
# Sorted array
arr1 = sorted(arr)
 
# Length of the array
N = len(arr)
 
# Function Call
maxgcd = findMaxGCD(arr, N)
 
# Print the result
print(maxlen(0, 0))


C#
// C# program for the above approach
using System;
using System.Collections.Generic;
 
class GFG{
     
static Dictionary, int> dp = new Dictionary, int>();
static int maxgcd, N;
static List arr;
static List arr1;
 
static int __gcd(int a, int b)
{
    if (b == 0)
        return a;
         
    return __gcd(b, a % b);
}
 
// Function to find GCD of pair with
// maximum GCD
static int findMaxGCD(List arr, int N)
{
     
    // Stores maximum element of arr[]
    int high = 0;
      
    // Find the maximum element
    for(int i = 0; i < N; i++)
        high = Math.Max(high, arr[i]);
          
    // Maintain a count array
    int[] count = new int[high + 1];
  
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
        count[arr[i]] += 1;
          
    // Stores the multiples of a number
    int counter = 0;
      
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
        int j = i;
          
        // Iterate from current potential
        // GCD till it is less than MAX
        while (j <= high)
        {
             
            // A multiple found
            if (count[j] > 0)
                counter += count[j];
                  
            // Increment potential GCD by
            // itself io check i, 2i, 3i...
            j += i;
              
            // If 2 multiples found max
            // GCD found
            if (counter == 2)
                return i;
        }
        counter = 0;
    }
    return 1;
}
      
// Function to find longest subsequence
// such that GCD of any two distinct
// integers is maximum
static int maxlen(int i, int j)
{
     
    // Create the key
    // Base Case
    if (i >= N || j >= N)
        return 0;
          
    // Check if the current state is
    // already calculated
    if (dp.ContainsKey(new Tuple(i, j)))
        return dp[new Tuple(i, j)];
        
    // Compare current GCD to the
    // maximum GCD
    if (__gcd(arr[i], arr1[j]) ==
             maxgcd && arr[i] != arr1[j])
    {
         
        // If true increment and
        // move the pointer
        dp[new Tuple(i, j)] = 1 + maxlen(
                                     i, j + 1);
        return dp[new Tuple(i, j)];
    }
      
    // Return max of either subsequences
    return (Math.Max(maxlen(i + 1, j),
                  maxlen(i, j + 1)));
}
 
// Driver code
static void Main()
{
    arr = new List(new int[]{ 1, 2, 8, 5, 6 });
    arr1 = arr;
      
    // Sorted array
    arr1.Sort();
      
    // Length of the array
    N = arr.Count;
      
    // Function Call
    maxgcd = findMaxGCD(arr, N);
      
    // Print the result
    Console.Write(maxlen(0, 0) + 1);
}
}
 
// This code is contributed by divyesh072019


输出:
3

时间复杂度: O(2 N )
辅助空间: O(N)

高效方法:为了优化上述方法,我们的想法是使用动态编程,因为上述解决方案中有很多重叠的子问题,这些子问题可以一次又一次地解决。因此,可以通过使用备忘或制表避免相同子问题的重新计算。使用字典存储两个索引之间子序列的最大长度,并在下一个递归调用中使用这些值。步骤如下:

  1. 执行上述所有步骤。
  2. 使用字典dp存储两个索引之间子序列的最大长度。
  3. 在进行递归调用时,只需在表dp [] []中检查该值是否先前已计算过。如果发现为真,则使用此值。否则,请调用其他索引范围的函数。
  4. 打印完成上述步骤后计算出的最大子序列长度。

 下面是上述方法的实现:

C++

// C++ program for the above approach
#include
using namespace std;
 
map, int>dp;
int maxgcd;
vectorarr, arr1;
int N;
 
// Function to find GCD of pair with
// maximum GCD
int findMaxGCD(vectorarr, int  N)
{
     
    // Stores maximum element of arr[]
    int high = 0;
     
    // Find the maximum element
    for(int i = 0; i < N; i++)
        high = max(high, arr[i]);
         
    // Maintain a count array
    int count[high + 1] = {0};
 
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
        count[arr[i]] += 1;
         
    // Stores the multiples of a number
    int counter = 0;
     
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
        int j = i;
         
        // Iterate from current potential
        // GCD till it is less than MAX
        while (j <= high)
        {
             
            // A multiple found
            if (count[j] > 0)
                counter += count[j];
                 
            // Increment potential GCD by
            // itself io check i, 2i, 3i...
            j += i;
             
            // If 2 multiples found max
            // GCD found
            if (counter == 2)
                return i;
        }
        counter = 0;
    }
    return 1;
}
     
// Function to find longest subsequence
// such that GCD of any two distinct
// integers is maximum
int maxlen(int i, int j)
{
    int  a = 0;
 
    // Create the key
    // Base Case
    if (i >= N or j >= N)
        return 0;
         
    // Check if the current state is
    // already calculated
    if (dp[{i, j}])
        return dp[{i, j}];
       
    // Compare current GCD to the
    // maximum GCD
    if (__gcd(arr[i], arr1[j]) ==
        maxgcd && arr[i] != arr1[j])
    {
         
        // If true increment and
        // move the pointer
        dp[{i, j}] = 1 + maxlen(i, j + 1);
        return dp[{i, j}];
    }
     
    // Return max of either subsequences
    return (max(maxlen(i + 1, j),
                maxlen(i, j + 1)));
}
   
// Driver Code
int main()
{
    arr = { 1, 2, 8, 5, 6 };
    arr1 = arr;
     
    // Sorted array
    sort(arr1.begin(), arr1.end());
     
    // Length of the array
    N = arr.size();
     
    // Function Call
    maxgcd = findMaxGCD(arr, N);
     
    // Print the result
    cout << (maxlen(0, 0));
}
 
// This code is contributed by Stream_Cipher

Java

// Java program for the above approach
import java.util.*;
import java.awt.Point;
public class Main
{
  static HashMap dp = new HashMap<>();
  static int maxgcd, N;
  static Vector arr;
  static Vector arr1;
 
  static int __gcd(int a, int b)
  {
    if (b == 0)
      return a;
 
    return __gcd(b, a % b);
  }
 
  // Function to find GCD of pair with
  // maximum GCD
  static int findMaxGCD(Vector arr, int N)
  {
 
    // Stores maximum element of arr[]
    int high = 0;
 
    // Find the maximum element
    for(int i = 0; i < N; i++)
      high = Math.max(high, arr.get(i));
 
    // Maintain a count array
    int[] count = new int[high + 1];
 
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
      count[arr.get(i)] += 1;
 
    // Stores the multiples of a number
    int counter = 0;
 
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
      int j = i;
 
      // Iterate from current potential
      // GCD till it is less than MAX
      while (j <= high)
      {
 
        // A multiple found
        if (count[j] > 0)
          counter += count[j];
 
        // Increment potential GCD by
        // itself io check i, 2i, 3i...
        j += i;
 
        // If 2 multiples found max
        // GCD found
        if (counter == 2)
          return i;
      }
      counter = 0;
    }
    return 1;
  }
 
  // Function to find longest subsequence
  // such that GCD of any two distinct
  // integers is maximum
  static int maxlen(int i, int j)
  {
 
    // Create the key
    // Base Case
    if (i >= N || j >= N)
      return 0;
 
    // Check if the current state is
    // already calculated
    if (dp.containsKey(new Point(i, j)))
      return dp.get(new Point(i, j));
 
    // Compare current GCD to the
    // maximum GCD
    if (__gcd(arr.get(i), arr1.get(j)) ==
        maxgcd && arr.get(i) != arr1.get(j))
    {
 
      // If true increment and
      // move the pointer
      dp.put(new Point(i, j), 1 + maxlen(i, j + 1));
      return dp.get(new Point(i, j));
    }
 
    // Return max of either subsequences
    return (Math.max(maxlen(i + 1, j), maxlen(i, j + 1)));
  }
 
  public static void main(String[] args) {
    arr = new Vector();
    arr.add(1);
    arr.add(2);
    arr.add(8);
    arr.add(5);
    arr.add(6);
    arr1 = arr;
 
    // Sorted array
    Collections.sort(arr1);
 
    // Length of the array
    N = arr.size();
 
    // Function Call
    maxgcd = findMaxGCD(arr, N);
 
    // Print the result
    System.out.println(maxlen(0, 0) + 1);
  }
}
 
// This code is contributed by divyeshrabadiya07.

Python3

# Python3 program for the above approach
import math
 
# Function to find GCD of pair with
# maximum GCD
def findMaxGCD(arr, N):
     
    # Stores maximum element of arr[]
    high = 0
     
    # Find the maximum element
    for i in range(0, N):
        high = max(high, arr[i])
 
    # Maintain a count array
    count = [0] * (high + 1)
     
    # Store the frequency of arr[]
    for i in range(0, N):
        count[arr[i]] += 1
 
    # Stores the multiples of a number
    counter = 0
 
    # Iterate over the  range [MAX, 1]
    for i in range(high, 0, -1):
        j = i
 
        # Iterate from current potential
        # GCD till it is less than MAX
        while (j <= high):
 
            # A multiple found
            if (count[j] > 0):
                counter += count[j]
 
            # Increment potential GCD by
            # itself io check i, 2i, 3i...
            j += i
 
            # If 2 multiples found max
            # GCD found
            if (counter == 2):
                return i
 
        counter = 0
 
# Function to find longest subsequence
# such that GCD of any two distinct
# integers is maximum
def maxlen(i, j):
   
    a = 0
     
    # Create the key
    key = (i, j)
 
    # Base Case
    if i >= N or j >= N:
        return 0
     
    # Check if the current state is
    # already calculated
    if key in dp:
        return dp[key]
       
    # Comapare current GCD to the
    # maximum GCD
    if math.gcd(arr[i], arr1[j]) == maxgcd and arr[i] != arr1[j]:
 
        # If true increment and
        # move the pointer
        dp[key] = 1 + maxlen(i, j + 1)
 
        return dp[key]
 
    # Return max of either subsequences
    return max(maxlen(i + 1, j), maxlen(i, j + 1))
 
 
# Drivers code
arr = [1, 2, 8, 5, 6]
 
# Empty dictionary
dp = dict()
 
# Sorted array
arr1 = sorted(arr)
 
# Length of the array
N = len(arr)
 
# Function Call
maxgcd = findMaxGCD(arr, N)
 
# Print the result
print(maxlen(0, 0))

C#

// C# program for the above approach
using System;
using System.Collections.Generic;
 
class GFG{
     
static Dictionary, int> dp = new Dictionary, int>();
static int maxgcd, N;
static List arr;
static List arr1;
 
static int __gcd(int a, int b)
{
    if (b == 0)
        return a;
         
    return __gcd(b, a % b);
}
 
// Function to find GCD of pair with
// maximum GCD
static int findMaxGCD(List arr, int N)
{
     
    // Stores maximum element of arr[]
    int high = 0;
      
    // Find the maximum element
    for(int i = 0; i < N; i++)
        high = Math.Max(high, arr[i]);
          
    // Maintain a count array
    int[] count = new int[high + 1];
  
    // Store the frequency of arr[]
    for(int i = 0; i < N; i++)
        count[arr[i]] += 1;
          
    // Stores the multiples of a number
    int counter = 0;
      
    // Iterate over the  range [MAX, 1]
    for(int i = high; i > 0; i--)
    {
        int j = i;
          
        // Iterate from current potential
        // GCD till it is less than MAX
        while (j <= high)
        {
             
            // A multiple found
            if (count[j] > 0)
                counter += count[j];
                  
            // Increment potential GCD by
            // itself io check i, 2i, 3i...
            j += i;
              
            // If 2 multiples found max
            // GCD found
            if (counter == 2)
                return i;
        }
        counter = 0;
    }
    return 1;
}
      
// Function to find longest subsequence
// such that GCD of any two distinct
// integers is maximum
static int maxlen(int i, int j)
{
     
    // Create the key
    // Base Case
    if (i >= N || j >= N)
        return 0;
          
    // Check if the current state is
    // already calculated
    if (dp.ContainsKey(new Tuple(i, j)))
        return dp[new Tuple(i, j)];
        
    // Compare current GCD to the
    // maximum GCD
    if (__gcd(arr[i], arr1[j]) ==
             maxgcd && arr[i] != arr1[j])
    {
         
        // If true increment and
        // move the pointer
        dp[new Tuple(i, j)] = 1 + maxlen(
                                     i, j + 1);
        return dp[new Tuple(i, j)];
    }
      
    // Return max of either subsequences
    return (Math.Max(maxlen(i + 1, j),
                  maxlen(i, j + 1)));
}
 
// Driver code
static void Main()
{
    arr = new List(new int[]{ 1, 2, 8, 5, 6 });
    arr1 = arr;
      
    // Sorted array
    arr1.Sort();
      
    // Length of the array
    N = arr.Count;
      
    // Function Call
    maxgcd = findMaxGCD(arr, N);
      
    // Print the result
    Console.Write(maxlen(0, 0) + 1);
}
}
 
// This code is contributed by divyesh072019
输出:
3

时间复杂度: O(N 2 )
辅助空间: O(N)