Published December 3, 2016
(updated December 3, 2016) by Ömercan Yazici

Calculating the divisor of a number N is an easy task. For example the divisors of the number 2048 can be easily calculated by the following source code:

Plain C++ Implementation

C++

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

#include <type_traits>

#include <iostream>

#include <list>

#include <cmath>

template<typenameT>

std::list<T>list_of_divisors(Tnumber){

static_assert(std::is_integral<T>::value,"T must be an integral type");

std::list<T>result;

if(number<1)

returnresult;

intsq=(int)std::floor(std::sqrt(number))+1;

for(inti=sq;i>0;--i){

if(number%i==0){

result.push_front(i);

if(i!=number/i){

result.push_back(number/i);

}

}

}

returnresult;

}

intmain(intargc,char**argv){

intN=2048;

std::list<int>result=list_of_divisors(N);

for(inta:result)

std::cout<<a<<" ";

std::cout<<std::endl;

return0;

}

The result is:

124816326412825651210242048

It was calculated on runtime. But does it have to be calculated on runtime? If the number N (like a compile time constant) is known beforehand there is no need for that. We need a solution purely determined on compile time.

But stop! It’s all right to ask the question:

Is there a case for a compile time constant where we also need the divisors – but runtime is a no go?

I think most of the time a runtime solution is fine. But now my case:

I have a predefined constant called SAMPLING_COUNT, which is pretty much is the accuracy of a spectrum. To divide the spectrum into equal sized intervals based on the quality factor Q (determined on runtime) I have to use the divisors of SAMPLING_COUNT.

Now still; does it have to be on compile time? I have to admit, no, it would be completely fine to calculate it on runtime. But when I have the possibility to calculate it on compile time, I will just do it. Maybe you can find a good reason?

The following solution is capable of calculating the divisors of small numbers and returning them in a sorted constant array. It uses C++11 features and was tested on:

1

2

gcc version5.4.020160609(Ubuntu5.4.0-6ubuntu1~16.04.4)

clang version3.8.0-2ubuntu4(tags/RELEASE_380/final)

Remember to add the switch --std=c++11 as a parameter for GCC and -std=c++11 for clang++.

Before we dig into the divisor class we need a constexpr variant of std::sqrt. The C++14 already has one; but due to the fact that nearly all of my own projects have the C++11 baseline and C++14 support is incomplete for MSVC, I wrote my own std::sqrt integer variant:

constexpr integer sqrt

C++

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

// sqrt using binary search method

template<typenameT>

classt_sqrt

{

static_assert(std::is_integral<T>::value,"T must be an integral type");

staticconstexprT_helper(Tv,Tlow,Thigh){

return(low==high?

low:

((v/(low+high+1)<(low+high+1)/4)?

_helper(v,low,(low+high+1)/2-1):

_helper(v,(low+high+1)/2,high))

);

}

public:

staticconstexprTvalue(Tv){

returnv>0?_helper(v,0,v/2+1):(T)0;

}

t_sqrt()=delete;

t_sqrt(constt_sqrt&)=delete;

t_sqrt(t_sqrt&&)=delete;

};

It is not that fancy as std::sqrt, as it has to be called this way:

intv=t_sqrt<int>::value(4);// == 2

An easy task for the reader would be to change the interface to the well known std::sqrt one, without exposing the internal _helper function to the public.

Now with our t_sqrt function we are able to build the divisor (builder) class:

Divisor class

C++

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

template<intN>

classDivisor

{

static_assert(N>=1,"N must be at least 1");

// First initialization

public:

staticconstexprauto number=N;

staticconstexprauto sqrt_number=t_sqrt<int>::value(number)+1;

// Stuff comes here [....]

// Utils

public:

Divisor()=delete;

Divisor(constDivisor&)=delete;

Divisor(Divisor&&)=delete;

};

First of it would be nice to know how long the produced array will be. We will calculate it with a recursive function:

Length calculation

C++

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

// [...]

private:

staticconstexprintcalc_length(inti){

return((i==0)?

0:

calc_length(i-1)+((number%i==0)?

((number/i==i)?1:2):

0

)

);

}

public:

staticconstexprauto length=calc_length(sqrt_number);

// [...]

The recursive function is pretty straightforward, as it calculates the divisors and only increases the total count when a divisor or divisor pair was found. A faster variant, but only after calculating the array, would be to use the line:

sizeof(Divisor<N>::values)/sizeof(int)

I do not like this style but you are free to use what ever variant you want.

To construct the array we need an array building template specialization. It is nearly the same as a recursive function with an explicit end:

Array construction

C++

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

// [...]

private:

// Recursive body

// M is like i in our loop, it decreases from sqrt_number to 0

// Rest is the array we build

template<intM,int...Rest>

structImpl

{

// std::coditional resembles an ? expression:

// 'cond ? T1 : T2' -> std::conditional<cond, T1, T2>

typedeftypenamestd::conditional<(number%M)==0,

typenamestd::conditional<M==(number/M),

Impl<M-1,M,Rest...>,// Equal pair found

Impl<M-1,M,Rest...,number/M>// Two distinct elements found

>::type,

Impl<M-1,Rest...>// Not a divisor

>::typeT;

staticconstexprauto&values=T::values;

};

// Recursive end

template<int...Rest>

structImpl<0,Rest...>

{

// We transform the template list to a constant array

staticconstexprintvalues[]={Rest...};

};

public:

staticconstexprauto&&values=Impl<sqrt_number>::values;

// [...]

To be fair, we are pretty much done. But to use the array in actual runtime code and to make sure the array is also in the binary of the program, we need to add this line:

Binary fix

C++

1

2

3

template<intN>

template<int...Rest>

constexprintDivisor<N>::Impl<0,Rest...>::values[];

This is all you have to do. It is easy to use the class in runtime code:

Example main function

C++

1

2

3

4

5

6

7

8

9

10

intmain(intargc,char**argv){

constexprintN=2048;

typedefDivisor<N>OurDivisor;

for(inti=0;i<OurDivisor::length;++i)

std::cout<<OurDivisor::values[i]<<" ";

std::cout<<std::endl;

return0;

}

The above program produces the same line as the runtime implementation:

124816326412825651210242048

This is all. If you found some mistakes or something which is completely wrong, please comment. I’m happy to improve and open for constructive criticism. I would also be happy if someone could test the code for MSVC.

Note:

You can construct many other algorithms with the style presented above. Like an integer sequence (see StackOverflow, as it has a lot of examples for that).

I think it would be also possible to construct a general class for a general function f. But that would look ugly and would make this little example much more complicated.

A good starting point is also the Boost MPL library, as it has much more complicated examples and is not bounded to C++11 (correct me if I’m wrong).

With C++14 everything got really easy. Just read about the features. You will understand why :)

I recommend to look a the following StackOverflow questions as it also helped me to construct the divisor class:

After experimenting with Qt and finite elements I started to play around with C# two months ago due to the Unity Engine. Many of my games need some kind of configuration files and I love my DataLisp implementation (and it does his job well), so I decided to implement the DataLisp standard (v.1) in C#. To be honest, it was really easy and the code got much lighter, due to the help of the .NET/Mono framework. If you want to take a look. I have a C# Repository on GitHub.

More Information about DataLisp and his C++ and C# implementation can you find in his own project page.

It’s yet another ray tracer with pure focus on spectral rendering and global illumination.
In the future I will post more information about the development process and the underlying principles and my own problems with it. Today some inside pics to the (broken) sampling procedure. Continue reading →

This error is not old, and the solution presented here is not new, yet I would like to introduce you to it, so you do not have to search through thousand google pages to find the right solution. Continue reading →

It’s been a long time since I wrote my last post…….. Much has changed.

I’m now a student at the University of Heidelberg. I’m studying Computer Science and do not know how much time I can now spend now on my blog. I do not think that I either spent that much time here, but I do not want to abandon my blog. I will write some post from time to time about my studies and everything else on my mind.

Pear3DEngine is a modern and modular 3D development framework that lets you create professional games, simulations and more. You are free to develop your program in C++, XML or LUA and publish it as open source software or selling it as a commercial program. The rendering engine uses internally OpenGL or DirectX optionally. The planned editor supports software development on Linux, Windows and maybe MacOS X. DirectX 9 and Windows XP are not supported and support is not planned in the future. One goal of the Pear3DEngine Framework is to use the latest and most promising algorithms and techniques from the 3D and IT scene.

This is the description of the engine that you can find on SourceForge. But why a new engine? Are there not enough in the world?