简体   繁体   中英

printbinary recursive algorithm

I can't wrap my head around how this simple recursive function works:

void printBinary(const int& n)
{
    if(n < 2)
    {
        cout << n;
    }
    else
    {
        printBinary(n / 2);
        printBinary(n % 2);
    }
}

I know it has something to do with n / 2 "chopping" off the last digit of the binary representation and n % 2 yielding such last digit of the binary representation, but when I recursively trace this code it just seems like magic. I can't come up with a simple logical explanation.

Edit: This is a great explanation of the algorithm, and leads me to kind of rephrase my question to: why does n % 2, or the remainder of a decimal number, give you the binary digits of such number. What is the logic behind that?

For a recursive algorithm, I always find it helpful to quickly write a small example out in a text file with indents to show the recurse levels:

f(42)
    f(21)
        f(10)
            f(5)
                f(2)
                    f(1)  - 1
                    f(0)  - 0
                f(1)  - 1
            f(0)  - 0
        f(1)  - 1
    f(0)  - 0

This is an equivalent tree in binary, that may help:

f(101010b)
    f(10101b)
        f(1010b)
            f(101b)
                f(10b)
                    f(1b)  - 1
                    f(0b)  - 0
                f(1b)  - 1
            f(0b)  - 0
        f(1b)  - 1
    f(0b)  - 0

What you'll see from this, is that the first recursive call (n/2) is going to keep dividing by 2 until it finds the most significant bit, the number of times it recurses is the number of bits in the answer. How many times can you divide 42 by 2 before you get to a 1 or 0? 6 times, so there are 6 total bits in the answer.

The next step is less obvious. When you drill down to the next to last level - f(2) or f(10b), what you've done is identified the two most significant digits. Look at a decimal value that might be less confusing.

f(1234)
    f(123)
        f(12)
            f(1)  - 1
            f(2)   - 2
        f(3)  - 3
    f(4)  - 4

When you keep dividing by 10, you always have some number of most significant digits. When you get to the last two digits (12), the first one is 12/10 and the second is 12%10. Going back up a level, (123), you've already recursively taken care of the first two most sig digits, f(12) and now you run f(3) which in the decimal case would be part of the base case (n <10).

Hope this helps

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM