📌  相关文章
📜  检查一个大数是否可以分成两个或多个相等的段

📅  最后修改于: 2022-05-13 01:57:08.785000             🧑  作者: Mango

检查一个大数是否可以分成两个或多个相等的段

给定一个非常大的数字 N。任务是检查该数字是否可以分成两个或多个相等和的段。
例子

Input: N = 73452  
Output: Yes
Segments of {7}, {3, 4}, {5, 2} which has equal sum of 7

Input: N = 1248
Output: No

可以按照以下步骤解决问题:

  1. 由于数字可能很大,因此将数字初始化为字符串。
  2. 使用 prefixSum 数组来存储数组的前缀和。
  3. 现在从第二个元素遍历到最后一个元素,因此第一段将是 0 到 i-1,其和为 Prefixsum[i-1]。
  4. 使用另一个从 i 遍历到 n 的指针,并继续添加总和。
  5. 如果任何阶段的总和等于 Prefixsum[i-1],则该段的总和等于 first。
  6. 将段总和值重新初始化为 0 并继续移动指针。
  7. 如果在任何阶段段总和超过第一个段的总和,则中断,因为段总和作为前缀和 [i-1] 的除法是不可能的。
  8. 如果指针到达最后一个数字,则检查最后一个段和是否等于第一个段和即prefixsum[i-1],则可以将其划分为等和的段。

下面是上述方法的实现。

C++
// C++ program to Check if a large number can be divided
// into two or more segments of equal sum
#include 
using namespace std;
 
// Function to check if a number
// can be divided into segments
bool check(string s)
{
    // length of string
    int n = s.length();
 
    // array to store prefix sum
    int Presum[n];
 
    // first index
    Presum[0] = s[0] - '0';
 
    // calculate the prefix
    for (int i = 1; i < n; i++) {
        Presum[i] = Presum[i - 1] + (s[i] - '0');
    }
 
    // iterate for all number from second number
    for (int i = 1; i <= n - 1; i++) {
 
        // sum from 0th index to i-1th index
        int sum = Presum[i - 1];
        int presum = 0;
        int it = i;
 
        // counter turns true when sum
        // is obtained from a segment
        int flag = 0;
 
        // iterate till the last number
        while (it < n) {
            // sum of segments
            presum += s[it] - '0';
 
            // if segment sum is equal
            // to first segment
            if (presum == sum) {
                presum = 0;
                flag = 1;
            }
            // when greater than not possible
            else if (presum > sum) {
                break;
            }
            it++;
        }
 
        // if at the end all values are traversed
        // and all segments have sum equal to first segment
        // then it is possible
        if (presum == 0 && it == n && flag == 1) {
            return true;
        }
    }
    return false;
}
 
// Driver Code
int main()
{
    string s = "73452";
    if (check(s))
        cout << "Yes";
    else
        cout << "No";
    return 0;
}


Java
// Java program to Check if a large number can be divided
// into two or more segments of equal sum
 
public class GFG {
 
    // Function to check if a number
    // can be divided into segments
    static boolean check(String s)
    {
        // length of string
        int n = s.length();
      
        // array to store prefix sum
        int[] Presum = new int[n];
      
        // first index
        char[] s1 = s.toCharArray();
        Presum[0] = s1[0] - '0';
      
        // calculate the prefix
        for (int i = 1; i < n; i++) {
            Presum[i] = Presum[i - 1] + (s1[i] - '0');
        }
      
        // iterate for all number from second number
        for (int i = 1; i <= n - 1; i++) {
      
            // sum from 0th index to i-1th index
            int sum = Presum[i - 1];
            int presum = 0;
            int it = i;
      
            // counter turns true when sum
            // is obtained from a segment
            int flag = 0;
      
            // iterate till the last number
            while (it < n) {
                // sum of segments
                presum += s1[it] - '0';
      
                // if segment sum is equal
                // to first segment
                if (presum == sum) {
                    presum = 0;
                    flag = 1;
                }
                // when greater than not possible
                else if (presum > sum) {
                    break;
                }
                it++;
            }
      
            // if at the end all values are traversed
            // and all segments have sum equal to first segment
            // then it is possible
            if (presum == 0 && it == n && flag == 1) {
                return true;
            }
        }
        return false;
    }
      
    // Driver Code
    public static void main(String[] args) {
         
        String s = "73452";
        if (check(s))
            System.out.println("Yes");
        else
            System.out.println("No");
    }
}
Python 3 # Python program to Check if a large number can be divided
# into two or more segments of equal sum

# Function to check if a number
# can be divided into segments
def check(s):

    # length of string
    n = len(s)

    # array to store prefix sum
    Presum = [None]*n

    # first index
    Presum[0] = ord(s[0]) - ord('0')

    # calculate the prefix
    for i in range(1, n):
        Presum[i] = Presum[i - 1] + (ord(s[i]) - ord('0'))

    # iterate for all number from second number
    for i in range(1, n):

        # sum from 0th index to i-1th index
        sum = Presum[i - 1]
        presum = 0
        it = i

        # counter turns true when sum
        # is obtained from a segment
        flag = 0

        # iterate till the last number
        while (it < n):
          
            # sum of segments
            presum = presum + ord(s[it]) - ord('0')

            # if segment sum is equal
            # to first segment
            if (presum == sum):
                presum = 0
                flag = 1
                
            # when greater than not possible
            elif (presum > sum):
                break

            it = it + 1

        # if at the end all values are traversed
        # and all segments have sum equal to first segment
        # then it is possible
        if (presum == 0 and it == n and flag == 1):
            return True
    return False

# Driver Code
if __name__ == '__main__':
    s = "73452"
    if (check(s)):
        print("Yes")
    else:
        print("No")

# This code is contributed by rakeshsahni


C#
// C# program to Check if a large
// number can be divided into two
// or more segments of equal sum
using System;
 
class GFG
{
 
    // Function to check if a number
    // can be divided into segments
    static bool check(String s)
    {
        // length of string
        int n = s.Length;
     
        // array to store prefix sum
        int[] Presum = new int[n];
     
        // first index
        char[] s1 = s.ToCharArray();
        Presum[0] = s1[0] - '0';
     
        // calculate the prefix
        for (int i = 1; i < n; i++)
        {
            Presum[i] = Presum[i - 1] + (s1[i] - '0');
        }
     
        // iterate for all number from second number
        for (int i = 1; i <= n - 1; i++)
        {
     
            // sum from 0th index to i-1th index
            int sum = Presum[i - 1];
            int presum = 0;
            int it = i;
     
            // counter turns true when sum
            // is obtained from a segment
            int flag = 0;
     
            // iterate till the last number
            while (it < n)
            {
                // sum of segments
                presum += s1[it] - '0';
     
                // if segment sum is equal
                // to first segment
                if (presum == sum)
                {
                    presum = 0;
                    flag = 1;
                }
                 
                // when greater than not possible
                else if (presum > sum)
                {
                    break;
                }
                it++;
            }
     
            // if at the end all values are traversed
            // and all segments have sum equal to first segment
            // then it is possible
            if (presum == 0 && it == n && flag == 1)
            {
                return true;
            }
        }
        return false;
    }
     
    // Driver Code
    public static void Main(String[] args)
    {
         
        String s = "73452";
        if (check(s))
            Console.WriteLine("Yes");
        else
            Console.WriteLine("No");
    }
}
 
// This code has been contributed by 29AjayKumar


Javascript


输出:
Yes

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