3

I recently found out about the 3n+1 problem and wanted to write a simple code to do the problem.

It all works but at high odd numbers such as 999,999,999 it goes to negative numbers and repeats an endless cycle and I have no clue why.

// if n is odd  n = 3n+1
// if n is even n = n/2
while (true)
{
    int n;
    Console.WriteLine("Enter a positive whole number greater than one: ");
    while (!Int32.TryParse(Console.ReadLine(), out n))
    {
        Console.WriteLine("Enter a positive whole number greater than one: ");
    }
    while (n != 1)
    {
        if (n % 2 == 0)
        {
            n /= 2;
            Console.WriteLine("n / 2     = " + n);
        }
        else
        {
            n = 3 * n + 1;
            Console.WriteLine("3 * n + 1 = " + n);
        }
    }
    Console.ReadLine();
    Console.Clear();
}

What am I doing wrong? Thanks!

Sulhan
  • 116
  • 1
  • 7
  • 2
    Sounds like you are running into [integer overflow](https://en.wikipedia.org/wiki/Integer_overflow) – Sumner Evans Dec 03 '17 at 07:40
  • 1
    The [collatz conjeture](https://en.wikipedia.org/wiki/Collatz_conjecture) has been checked for all number smaller than 87×2^60 (via the yoyo@home project) - you need integers with more than [66 bits](https://www.wolframalpha.com/input/?i=ln_2(87%C3%972%5E60)) to compete. int32 and int64 are too small. Use [decimal](https://docs.microsoft.com/en-us/dotnet/csharp/language-reference/keywords/decimal) ([10^28 ~> 2^93](https://www.wolframalpha.com/input/?i=ln_2(10%5E28))) or [BigInteger](https://msdn.microsoft.com/en-us/library/system.numerics.biginteger(v=vs.110).aspx). Edit: disregarding runtime. – Theraot Dec 03 '17 at 07:49

2 Answers2

4

This is happening due to integer overflow:

In computer programming, an integer overflow occurs when an arithmetic operation attempts to create a numeric value that is outside of the range that can be represented with a given number of bits – either larger than the maximum or lower than the minimum representable value.

You could make use of a 64-bit integer type, in order to have a bigger range of integer numbers. Apparently an overflow can be noticed also in the latter case, but it will happen in a very large number. With 64-bit integer you can represent

18,446,744,073,709,551,615 numbers   

Whereas with 32-bit integers you can represent

4,294,967,295 numbers

In case of Int32 and Int64 you should divide the above numbers by two and take the quotient, this would be the maximum positive number that can be represented. This should be done, because both Int32 and Int64 are signed integers.

A better approach would be to make use of UInt64, see here, which can be used to represent unsigned integers with values ranging from 0 to 18,446,744,073,709,551,615.

Definetely an overflow can be noticed also in this case.

Christos
  • 53,228
  • 8
  • 76
  • 108
2

int is maximum 2,147,483,647. 3n when n is 999,999,999 is going to be bigger and overflow which will cause n to be negative after n = 3 * n + 1;

Oleg
  • 6,124
  • 2
  • 23
  • 40