📜  对于两个给定数组,满足条件X%A [i] = B [i]的X的最小值

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

给定两个数组A []B [] ,它们都由N个正整数,一个整数P组成,并且数组A []的元素是成对的互质数,任务是找到最小的整数X ,该整数至少为P在索引[0,N – 1]的范围内,所有i的X%A [i]等于B [i ]

例子:

方法:解决给定问题的想法是使用中国余数定理。请按照以下步骤解决给定的问题:

  • 计算数组A [],其等于存在于所述阵列A中的所有元素的乘积的LCM [],,因为所有的元素是互质。
  • 使用中国余数定理,找到所需的最小正整数Y。因此,对于某个整数KX的值由(Y + K * M)给出,对于所有i在索引[0,N – 1]范围内, X均满足X%A [i] = B [i ]
  • K的值可以从等式Y + K * M> = P中找到,它等于K> =(P – Y)/ M。
  • 因此,所需的最小可能整数X(Y + K * M)

下面是上述方法的实现:

C++
// C++ program for the above appraoch
#include
using namespace std;
 
// Function to calculate modulo
// inverse of a w.r.t m using
// Extended Euclid Algorithm
int inv(int a, int m)
{
    int m0 = m, t, q;
    int x0 = 0, x1 = 1;
 
    // Base Case
    if (m == 1)
        return 0;
 
    // Perform extended
    // euclid algorithm
    while (a > 1)
    {
        // q is quotient
        q = a / m;
 
        t = m;
 
        // m is remainder now,
        // process same as
        // euclid's algorithm
        m = a % m;
        a = t;
 
        t = x0;
        x0 = x1 - q * x0;
        x1 = t;
    }
 
    // If x1 is negative
    if (x1 < 0)
 
        // Make x1 positive
        x1 += m0;
 
    return x1;
}
 
// Function to implement Chinese
// Remainder Theorem to find X
int findMinX(int A[], int B[], int N)
{
     
    // Stores the product
    // of array elements
    int prod = 1;
 
    // Traverse the array
    for(int i = 0; i < N; i++)
 
        // Update product
        prod *= A[i];
 
    // Initialize the result
    int result = 0;
 
    // Apply the above formula
    for(int i = 0; i < N; i++)
    {
        int pp = prod / A[i];
        result += B[i] * inv(pp, A[i]) * pp;
    }
    return result % prod;
}
 
// Function to calculate the product
// of all elements of the array a[]
int product(int a[], int n)
{
     
    // Stores product of
    // all array elements
    int ans = 1;
 
    // Traverse the array
    for(int i = 0; i < n; i++)
    {
        ans *= a[i];
    }
 
    // Return the product
    return ans;
}
 
// Function to find the value of X
// that satisfies the given condition
void findSmallestInteger(int A[], int B[],
                         int P, int n)
{
     
    // Stores the required smallest value
    // using Chinese Remainder Theorem
    int Y = findMinX(A, B, n);
 
    // Stores the product
    // of all array elements
    int M = product(A,n);
 
    // The equation is Y + K*M >= P
    // Therefore, calculate K = ceil((P-Y)/M)
    int K = ceil(((double)P - (double)Y) /
                  (double)M);
 
    // So, X = Y + K*M
    int X = Y + K * M;
 
    // Print the resultant value of X
    cout << X;
}
 
// Driver Code
int main()
{
    int A[] = { 3, 4, 5 };
    int B[] = { 2, 3, 1 };
    int n = sizeof(A) / sizeof(A[0]);
    int P = 72;
 
    findSmallestInteger(A, B, P,n);
}
 
// This code is contributed by SURENDRA_GANGWAR


Java
// Java program for the above appraoch
 
import java.io.*;
import java.lang.*;
import java.util.*;
public class Main {
 
    // Function to calculate modulo
    // inverse of a w.r.t m using
    // Extended Euclid Algorithm
    static int inv(int a, int m)
    {
        int m0 = m, t, q;
        int x0 = 0, x1 = 1;
 
        // Base Case
        if (m == 1)
            return 0;
 
        // Perform extended
        // euclid algorithm
        while (a > 1) {
 
            // q is quotient
            q = a / m;
 
            t = m;
 
            // m is remainder now,
            // process same as
            // euclid's algorithm
            m = a % m;
            a = t;
 
            t = x0;
 
            x0 = x1 - q * x0;
 
            x1 = t;
        }
 
        // If x1 is negative
        if (x1 < 0)
 
            // Make x1 positive
            x1 += m0;
 
        return x1;
    }
 
    // Function to implement Chinese
    // Remainder Theorem to find X
    static int findMinX(int A[], int B[], int N)
    {
        // Stores the product
        // of array elements
        int prod = 1;
 
        // Traverse the array
        for (int i = 0; i < N; i++)
 
            // Update product
            prod *= A[i];
 
        // Initialize the result
        int result = 0;
 
        // Apply the above formula
        for (int i = 0; i < N; i++) {
            int pp = prod / A[i];
            result += B[i] * inv(pp, A[i]) * pp;
        }
 
        return result % prod;
    }
 
    // Function to calculate the product
    // of all elements of the array a[]
    static int product(int a[])
    {
        // Stores product of
        // all array elements
        int ans = 1;
 
        // Traverse the array
        for (int i = 0; i < a.length; i++) {
            ans *= a[i];
        }
 
        // Return the product
        return ans;
    }
 
    // Function to find the value of X
    // that satisfies the given condition
    public static void findSmallestInteger(int A[], int B[],
                                           int P)
    {
        // Stores the required smallest value
        // using Chinese Remainder Theorem
        int Y = findMinX(A, B, A.length);
 
        // Stores the product
        // of all array elements
        int M = product(A);
 
        // The equation is Y + K*M >= P
        // Therefore, calculate K = ceil((P-Y)/M)
        int K = (int)Math.ceil(((double)P - (double)Y)
                               / (double)M);
 
        // So, X = Y + K*M
        int X = Y + K * M;
 
        // Print the resultant value of X
        System.out.println(X);
    }
 
    // Driver Code
    public static void main(String[] args)
    {
        int A[] = { 3, 4, 5 };
        int B[] = { 2, 3, 1 };
 
        int P = 72;
 
        findSmallestInteger(A, B, P);
    }
}


Python3
# Python3 program for the above appraoch
import math
 
# Function to calculate modulo
# inverse of a w.r.t m using
# Extended Euclid Algorithm
def inv(a, m):
     
    m0 = m
    x0 = 0
    x1 = 1
 
    # Base Case
    if (m == 1):
        return 0
 
    # Perform extended
    # euclid algorithm
    while (a > 1):
         
        # q is quotient
        q = a // m
 
        t = m
 
        # m is remainder now,
        # process same as
        # euclid's algorithm
        m = a % m
        a = t
 
        t = x0
        x0 = x1 - q * x0
        x1 = t
 
    # If x1 is negative
    if (x1 < 0):
 
        # Make x1 positive
        x1 += m0
 
    return x1
 
# Function to implement Chinese
# Remainder Theorem to find X
def findMinX(A, B, N):
     
    # Stores the product
    # of array elements
    prod = 1
 
    # Traverse the array
    for i in range(N):
 
        # Update product
        prod *= A[i]
 
    # Initialize the result
    result = 0
 
    # Apply the above formula
    for i in range(N):
        pp = prod // A[i]
        result += B[i] * inv(pp, A[i]) * pp
         
    return result % prod
 
# Function to calculate the product
# of all elements of the array a[]
def product(a, n):
     
    # Stores product of
    # all array elements
    ans = 1
 
    # Traverse the array
    for i in range(n):
        ans *= a[i]
 
    # Return the product
    return ans
 
# Function to find the value of X
# that satisfies the given condition
def findSmallestInteger(A, B, P, n):
     
    # Stores the required smallest value
    # using Chinese Remainder Theorem
    Y = findMinX(A, B, n)
 
    # Stores the product
    # of all array elements
    M = product(A, n)
 
    # The equation is Y + K*M >= P
    # Therefore, calculate K = ceil((P-Y)/M)
    K = math.ceil((P - Y) / M)
 
    # So, X = Y + K*M
    X = Y + K * M
 
    # Print the resultant value of X
    print(X)
 
# Driver Code
if __name__ == "__main__" :
 
    A = [ 3, 4, 5 ]
    B = [ 2, 3, 1 ]
    n = len(A)
    P = 72
 
    findSmallestInteger(A, B, P, n)
 
# This code is contributed by AnkThon


C#
// C# program for the above appraoch
using System;
public class GFG
{
 
  // Function to calculate modulo
  // inverse of a w.r.t m using
  // Extended Euclid Algorithm
  static int inv(int a, int m)
  {
    int m0 = m, t, q;
    int x0 = 0, x1 = 1;
 
    // Base Case
    if (m == 1)
      return 0;
 
    // Perform extended
    // euclid algorithm
    while (a > 1) {
 
      // q is quotient
      q = a / m;
 
      t = m;
 
      // m is remainder now,
      // process same as
      // euclid's algorithm
      m = a % m;
      a = t;
 
      t = x0;
 
      x0 = x1 - q * x0;
 
      x1 = t;
    }
 
    // If x1 is negative
    if (x1 < 0)
 
      // Make x1 positive
      x1 += m0;
 
    return x1;
  }
 
  // Function to implement Chinese
  // Remainder Theorem to find X
  static int findMinX(int[] A, int[] B, int N)
  {
    // Stores the product
    // of array elements
    int prod = 1;
 
    // Traverse the array
    for (int i = 0; i < N; i++)
 
      // Update product
      prod *= A[i];
 
    // Initialize the result
    int result = 0;
 
    // Apply the above formula
    for (int i = 0; i < N; i++) {
      int pp = prod / A[i];
      result += B[i] * inv(pp, A[i]) * pp;
    }
 
    return result % prod;
  }
 
  // Function to calculate the product
  // of all elements of the array a[]
  static int product(int[] a)
  {
    // Stores product of
    // all array elements
    int ans = 1;
 
    // Traverse the array
    for (int i = 0; i < a.Length; i++) {
      ans *= a[i];
    }
 
    // Return the product
    return ans;
  }
 
  // Function to find the value of X
  // that satisfies the given condition
  public static void findSmallestInteger(int[] A, int[] B,
                                         int P)
  {
    // Stores the required smallest value
    // using Chinese Remainder Theorem
    int Y = findMinX(A, B, A.Length);
 
    // Stores the product
    // of all array elements
    int M = product(A);
 
    // The equation is Y + K*M >= P
    // Therefore, calculate K = ceil((P-Y)/M)
    int K = (int)Math.Ceiling(((double)P - (double)Y)
                              / (double)M);
 
    // So, X = Y + K*M
    int X = Y + K * M;
 
    // Print the resultant value of X
    Console.WriteLine(X);
  }
 
  // Driver Code
  public static void Main(string[] args)
  {
    int[] A = { 3, 4, 5 };
    int[] B = { 2, 3, 1 };
 
    int P = 72;
 
    findSmallestInteger(A, B, P);
  }
}
 
// This code is contributed by ukasp.


输出:
131

时间复杂度: O(N * log N)
辅助空间: O(1)