0

Suppose I have the following code to loop over numbers as follows:

 int p;
 cin>>p;
 for(unsigned long long int i=3*pow(10,p);i<6*pow(10,p);i++){

              //some code goes here
 }

Now, based on certain condition checks I need to print a i in between the range : 3*pow(10,p)<= i <6*pow(10,p)

The code works fine upto p=8, then it becomes pretty sluggish and the compiler seems to get stuck for p=9,10,11 and onwards. I am guessing the problem lies in using the correct data type. What should be the correct data type to be used here ?

The purpose of this loop is to find the decent numbers in between the range. Decent numbers conditions as follows: 1) 3, 5, or both as its digits. No other digit is allowed. 2) Number of times 3 appears is divisible by 5. 3) Number of times 5 appears is divisible by 3.

NOTE: I used unsigned long long int here (0 to 18,446,744,073,709,551,615) . I am running on a 32-bit machine.

Abrar
  • 6,874
  • 9
  • 28
  • 41

1 Answers1

2

You could use <cstdint> and its int64_t (which is guaranteed to have 64 bits) and you should compute the power outside of the loop; and long long has at least 64 bits in recent C or C++ standards.

But, as mentioned in a comment by 1201ProgramAlarm, 3e11 (i.e. 300 billions) loops is a lot, even on our fast machines. It could take minutes or hours: an elementary operation is needing a nanosecond (or half of it). 3e9 operations need several seconds; 3e11 operations need several minutes. Your loop body could do several thousands (or even more) elementary operations (i.e. machine code instructions).

It is not the compiler which is stuck: compiling your code is easy and quick (as long as the program has a reasonable size, e.g. less than ten thousand lines of code, without weird preprocessor or template expansion tricks expanding them pathologically). It is the computer running the compiled executable.

If you benchmark your code, don't forget to enable optimizations in your compiler (e.g. compiling with g++ -Wall -O2 -arch=native if using GCC...)

You should think a lot more on your problem and reformulate it to have a smaller search space.

Actually, your decent numbers might more be thought as strings of digits representing them; after all, a number does not have digits (in particular a number expressed in binary or ternary notation cannot have 3 as its digit), only some representation of a number have digits.

Then you should only consider the strings of 3 or 5 which are shorter than 12 characters, and you have much less of them (less than 10000, and probably less than 213 i.e. 8192); iterating ten thousand times should be quick. So generate every string smaller than e.g. 15 characters with only 3 and 5 in it, and test if it is decent.

Community
  • 1
  • 1
Basile Starynkevitch
  • 223,805
  • 18
  • 296
  • 547
  • Is there any possible way to make the operation faster ? like if I code it in C instead of C++ ? – Abrar Nov 06 '15 at 05:31
  • 2
    No. What you might do is think again on the overall program, perhaps do some math, and redesign a better algorithm. Since we don't know what your program is supposed to do we cannot help at all. – Basile Starynkevitch Nov 06 '15 at 05:32
  • Actually I am trying the find the Decent numbers in between those range . – Abrar Nov 06 '15 at 05:34
  • That should go into the question (which you should edit), not into a comment. You should define what is a decent number, and think about mathematical properties of them. – Basile Starynkevitch Nov 06 '15 at 05:35
  • I have a function in my code which returns a boolean based on whether the number is decent or not by converting it to string and checking for each digit. The function works fine for `55555533333 (11 digit)` – Abrar Nov 06 '15 at 05:51
  • Congratulations... Are you expecting us to do your homework? You really shouldn't. I improved my answer to give more help, but I won't do your homework at your place. And your approach is wrong: think in terms of *strings* not *numbers* – Basile Starynkevitch Nov 06 '15 at 05:53