USACO Training "Humble Numbers"

USACO Training "Humble Numbers"

Problem Statement

In this problem we are asked to find the n-th "humble number" of a set of primes of length K <= 100.
A humble number of a set is defined as a number whose prime factors are as subset of the set.
We are asked to find the n-th humble number of a set, when considered from lowest to greatest.

Notices

  1. Possibly most importantly, we notice that any humble number of a set can be created by multiplying elements of the set together.
  2. Clearly a recursive search (i.e. recursively multiplying elements by other elements) will take both too long (O(n^n)) and use too much memory (O(n!)). We try a DP approach.

DP Approach

We calculate the humble numbers in order (i.e. from the first to the Nth). For simplicity (and correctness), we assume that 1 is the 0th humble number.
Once we have the first X humble numbers, we compute the X+1-th humble number as follows:

  1. Set best=0x7FFFFFFF (largest signed long int) and bestPrime=-1
  2. For each prime P:
  3. find the smallest previous humble number H such that H*P is greater than the last (Xth) humble number;
  4. if this is smaller than best set best to this new value and set bestPrime to P;
  5. go back to step 2 until all primes are done
  6. set the X+1th humble number to be best

Optimizations

A rather glaring optimization is that H*P for the same P will always increase as X increases. So, we can set a "start value" for each prime in an array so we won't re-check unnecessarily previous H values that were deemed too small.

The second is that the humble number array will always be sorted, so we can use  <algorithm>'s std::upper_bound. But we need to find the humble number H such that H*P is greater than the Xth humble number, not directly comparing H! We think of comparing H with (Xth)/P, but std::upper_bound automatically casts double values to const int& values. Therefore, we use <functional>'s std::less<> - then, std::upper_bound does not need to (and will not) can (Xth)/P to a int.

Code

 

Comments

Popular posts from this blog

USACO Training "subset": Subset Sums

USACO 2018 Open: Talent Show

UVA 787 and Big Number Multiplication