Print all unique combination of factors of a given number

后端 未结 9 713
挽巷
挽巷 2021-02-08 05:46

What is the most efficient algorithm to print all unique combinations of factors of a positive integer. For example if the given number is 24 then the output should be

相关标签:
9条回答
  • 2021-02-08 06:43

    1) If i < num and i > num/2, then num % i == num - i. (Easy to prove.) So your for loop will pointlessly check all the integers greater than num/2 and the if statement will only succeed once, with temp == 2. I don't think that's what you wanted.

    2) In you fixed that, the recursion might need to produce a lot of answers. But you only print temp * once. So the output will look a bit wierd.

    3) isprime is unnecessary. num is always a legitimate factor, whether or not it is prime, provided you follow the point below.

    4) Finally, you need to figure out how to avoid printing out the same factorization multiple times. The easy solution is to only produce factorizations where the factors are monotonically non-increasing (as in your example). In order to do that, the recursion needs to produce factorizations with some maximum factor (which would be the previously discovered factor.) So the recursive function should have (at least) two arguments: the number to factor and the maximum allowed factor. (You also need to deal with the problem I noted as point 4.)

    The following Python code does (I believe) solve the problem, but it still does quite a few unnecessary divides. In a deviation from python style, it prints each factorization instead of acting as a generator, because that will be easier to translate into Java.

    # Uses the last value in accum as the maximum factor; a cleaner solution
    # would have been to pass max_factor as an argument.
    def factors(number, accum=[]):
      if number == 1:
        print '*'.join(map(str, accum))
      else:
        if accum:
          max_factor = min(accum[-1], number)
        else:
          max_factor = number
        for trial_factor in range(max_factor, 1, -1):
          remnant = number / trial_factor
          if remnant * trial_factor == number:
            factors(remnant, accum + [trial_factor,])
    

    It is possible to optimize the for statement. For example, once you compute remnant, you know that the next remnant must be at least one greater, so you can skip a bunch of trial_factor values when remnant is small.

    0 讨论(0)
  • 2021-02-08 06:43

    I have a solution without recursion or sorting or stacks in C/C++.

    #include <vector>
    #include <iostream>
    
    // For each n, for each i = n-1 to 2, try prod = prod*i, if prod < N.
    
    int
    g(int N, int n, int k)
    {
            int i = k;
            int prod = n;
            std::vector<int> myvec;
    
            myvec.push_back(n);
            while (i > 1) {
                    if (prod * i == N) {
                            prod = prod*i;
                            myvec.push_back(i);
                            for (auto it = myvec.begin();
                                    it != myvec.end(); it++) {
                                    std::cout << *it << ",";
                            }
                            std::cout << std::endl;
                            return i;
                    } else if (prod * i < N) {
                            prod = prod*i;
                            myvec.push_back(i);
                    } else { i--;}
            }
    
            return k;
    }
    
    void
    f(int N)
    {
            for (int i = 2; i <= N/2; i++) {
                    int x = g(N, i, i-1);
                    // Extract all possible factors from this point
                    while (x > 0) {
                            x = g(N, i, x-1);
                    }
            }
    }
    
    int
    main()
    {
            f(24);
    
            return 0;
    }
    

    And output is like this:

    $ ./a.out
        3,2,2,2,
        4,3,2,
        6,4,
        6,2,2,
        8,3,
        12,2,
    
    0 讨论(0)
  • 2021-02-08 06:44

    This code find all the factors of a number, sort them (locally and globally):

    public class PrimeFactors {
    
       final SortedSet< List< Integer >> _solutions = new TreeSet<>(
          new Comparator<List<Integer>>(){
             @Override
             public int compare( List<Integer> left, List<Integer> right ) {
                int count = Math.min( left.size(), right.size());
                for( int i = 0; i < count; ++i ) {
                   if( left.get(i) < right.get(i)) {
                      return -1;
                   }
                   if( left.get(i) > right.get(i)) {
                      return +1;
                   }
                 }
                return left.size() - right.size();
             }});
    
       public SortedSet< List< Integer >> getPrimes( int num ) {
          _solutions.clear();
          getPrimes( num, new LinkedList< Integer >());
          return _solutions;
       }
    
       private void getPrimes( int num, List< Integer > solution ) {
          for( int i = num - 1; i > 1; --i ) {
             if(( num % i ) == 0 ) {
                int temp = num / i;
                List< Integer > s = new LinkedList<>();
                s.addAll( solution );
                s.add( temp );
                s.add( i );
                Collections.sort( s );
                if( _solutions.add( s )) { // if not already found
                   s = new LinkedList<>();
                   s.addAll( solution );
                   s.add( temp );
                   getPrimes( i, s );
                 }
             }
          }
       }
       public static void main( String[] args ) {
          SortedSet< List< Integer >> solutions =
             new PrimeFactors().getPrimes( 24 );
          System.out.println( "Primes of 24 are:" );
          for( List< Integer > l : solutions ) {
             System.out.println( l );
          }
       }
    }
    

    Outputs:

    Primes of 24 are:
    [2, 2, 2, 3]
    [2, 2, 6]
    [2, 3, 4]
    [2, 12]
    [3, 8]
    [4, 6]
    
    0 讨论(0)
提交回复
热议问题