Search

4.9 — Boolean values

In real-life, it’s common to ask or be asked questions that can be answered with “yes” or “no”. “Is an apple a fruit?” Yes. “Do you like asparagus?” No.

Now consider a similar statement that can be answered with a “true” or “false”: “Apples are a fruit”. It’s clearly true. Or how about, “I like asparagus”. Absolutely false (yuck!).

These kinds of sentences that have only two possible outcomes: yes/true, or no/false are so common, that many programming languages include a special type for dealing with them. That type is called a Boolean type (note: Boolean is properly capitalized in the English language because it’s named after its inventor, George Boole).

Boolean variables

Boolean variables are variables that can have only two possible values: true, and false.

To declare a Boolean variable, we use the keyword bool.

To initialize or assign a true or false value to a Boolean variable, we use the keywords true and false.

Just as the unary minus operator (-) can be used to make an integer negative, the logical NOT operator (!) can be used to flip a Boolean value from true to false, or false to true:

Boolean values are not actually stored in Boolean variables as the words “true” or “false”. Instead, they are stored as integers: true becomes the integer 1, and false becomes the integer 0. Similarly, when Boolean values are evaluated, they don’t actually evaluate to “true” or “false”. They evaluate to the integers 0 (false) or 1 (true). Because Booleans actually store integers, they are considered an integral type.

Printing Boolean variables

When we print Boolean values with std::cout, std::cout prints 0 for false, and 1 for true:

Outputs:

1
0
0
1

If you want std::cout to print “true” or “false” instead of 0 or 1, you can use std::boolalpha. Here’s an example:

This prints:

1
0
true
false

You can use std::noboolalpha to turn it back off.

Integer to Boolean conversion

You can’t initialize a Boolean with an integer using uniform initialization:

(note: some versions of g++ don’t enforce this properly)

However, in any context where an integer can be converted to a Boolean , the integer 0 is converted to false, and any other integer is converted to true.

This prints:

true
false

Inputting Boolean values

Inputting Boolean values using std::cin sometimes trips new programmers up.

Consider the following program:

Enter a Boolean value: true
You entered: 0

Wait, what?

It turns out that std::cin only accepts two inputs for Boolean variables: 0 and 1 (not true or false). Any other inputs will cause std::cin to silently fail. In this case, because we entered true, std::cin silently failed and didn’t assign a value to variable b. Consequently, when std::cout printed a value for b, it printed whatever value was in variable b (previously initialized to 0).

Boolean return values

Boolean values are often used as the return values for functions that check whether something is true or not. Such functions are typically named starting with the word is (e.g. isEqual) or has (e.g. hasCommonDivisor).

Consider the following example, which is quite similar to the above:

Here’s output from two runs of this program:

Enter an integer: 5
Enter another integer: 5
5 and 5 are equal? true
Enter an integer: 6
Enter another integer: 4
6 and 4 are equal? false

How does this work? First we read in integer values for x and y. Next, the expression “isEqual(x, y)” is evaluated. In the first run, this results in a function call to isEqual(5, 5). Inside that function, 5 == 5 is evaluated, producing the value true. The value true is returned back to the caller to be printed by std::cout. In the second run, the call to isEqual(6, 4) returns the value false.

Boolean values take a little bit of getting used to, but once you get your mind wrapped around them, they’re quite refreshing in their simplicity! Boolean values are also a huge part of the language -- you’ll end up using them more than all the other fundamental types put together!

We’ll continue our exploration of Boolean values in the next lesson.


4.10 -- Introduction to if statements
Index
4.8 -- Floating point numbers

521 comments to 4.9 — Boolean values

  • Jose

    Hi, I´m using VS 2019 and boolean copy initialization gives a compiler error unless 1 or 0 is used.

    • Please always post the error message if you're getting an error.
      I assume you're seeing this warning and your compiler is treating warnings as errors
      " warning C4305: 'initializing': truncation from 'int' to 'bool'"
      or similar.
      You can silence this by negating the int twice

      • Jose

        The error is in spanish, that´s why I didn´t post it but basically that´s what it is saying.

        I find this example a bit contradictory when setting up the IDE we´ve been told to check "Treat warnings as errors".

  • Jack

    Just a brief note, there is a typo!

    "

    If you want std::cout to print “true” or “false” instead of 0 or 1, you can use std::boolalpha:

    "

    Should read

    "

    If you want std::cout to print “true” or “false” instead of 0 or 1, you can use std::boolalpha;

    or

    If you want std::cout to print “true” or “false” instead of 0 or 1, you can use std::boolalpha

    "

  • alfonso

    In section:
    "Integer to Boolean conversion

    You can’t initialize a Boolean with an integer using uniform initialization"

    I have Arch Linux with Code::Blocks configured as in previous lessons and still the program compiles and run as expected when

    Output:
    true

    This is the log section:

    -------------- Build: Debug in random_stuff (compiler: GNU GCC Compiler)---------------

    g++ -Wall -fexceptions -g -Weffc++ -pedantic-errors -Wextra -Wall -std=c++1z -Wsign-conversion -Werror  -c /home/alfonso/work/c++/CBProjects/random_stuff/random_stuff/main.cpp -o obj/Debug/main.o
    g++  -o bin/Debug/random_stuff obj/Debug/main.o  
    Output file is bin/Debug/random_stuff with size 104.32 KB
    Process terminated with status 0 (0 minute(s), 1 second(s))
    0 error(s), 0 warning(s) (0 minute(s), 1 second(s))

    • Hi!

      Your code compiles with versions prior to g++9. Make sure you're running the latest version.
      g++ has several issues, I recommend you switching to clang++. It uses a g++-like command line interface, all your compiler flags will continue to work.

  • Leon

    I'm having trouble understanding your first example in the section "inputting Boolean values": Although the variable b is not initialized, i.e. contains random junk, shouldn't std::cout refer to it's type (which is clearly defined as bool!) and thus print either 0 (if the "junk" is a "number" with "value" 0) or 1 (if it is anything else)?
    In my reasoning, std::cout does not know, if a variable has been initialized or not and just treats the given data said suggested by it's type. Can you clarify?

    Great work!

    Leon

    • First off, this section is no longer true (Since C++11). @std::cin.operator>> will set @b to to false if extraction fails (@Alex).
      Let's assume @b contains junk for some other reason

      If @std::boolalpha is not set, @std::cin.operator<< converts bools to ints before printing them, thus you can observer numbers other than 0 and 1.

      Note: The compiler clang++ seems the only check the least significant bit during boolean operations. This means that every even number is false, and every odd number is true.

  • John

    Can I assume my logic is correct? It worked with a few tests I made. Please check my code..

    • Alex

      If you test with every number from 1 to 9 and they all return the expected answer, then your logic is correct.

      However, the second else if statement seems redundant (as inputs as required to be a single digit per the problem statement).

    • John

      I tried to write a program that work for any number of digits. But it seems it's not that simple. When 2 higher primes multiply, my logic goes wrong. I did some research and found how to make that happen. But whenever I do such research, I found things like q(sqrt(n)) complexity blah blah and equations with 'E' like thing that I have no idea what it means. Feels like this is going to be a hard road.

  • Red Lightning

    --That example is not good because 4 is a constant value and with warnings treated as errors (Which are recommended in this website) the compiler will abort the process of creating the object file. I think this is bad and frustrating for new users because some won't understand why the error is happening, resulting in them being unable to fix it (or at least remove/comment out the if without knowing what they are doing).

  • Elvis

    I made one that works for every prime number by checking if the number has any remainder when it is divided by two

    also made two automatically a prime number

    • * Line 21: Initialize your variables with brace initializers.
      * Line 15, 23: Limit your lines to 80 characters in length for better readability on small displays.

      Prime numbers aren't that simple. According to your program, every odd number is a prime.

  • Old M8

    Is this alright?

    (Else if is never really explained in the material and the quiz tripped me up with the wording so I originally thought I was looking for any prime numbers not specific ones)

    Also any lively discord servers or communication channels for c++ noobs?

    • * Line 33: Limit your lines to 80 characters in length for better readability on small displays.

      Always print a line feed at the end of your program to not mess up the terminal/console output.

  • Quick suggestion: I think you meant "nonsensical" instead of "non-nonsensical", as that's a double negative that equates to "sensical".

    Your tutorials are AMAZING! I've been learning C++ so fast :D

  • Gejsi

    Hello!
    I seem to fail to understand the purpose of bool "isEqual(x, y)" being used in the above example when I can simply do
    <code>
    #include <iostream>

    int main()
    {
        int x{0};
        int y{0};
        std::cout << "Enter an integer: ";
        std::cin >> x;
        std::cout << "Enter a second integer: ";
        std::cin >> y;
        if (x == y)
            std::cout << "Your " << x << " is equal with " << y;
        else
            std::cout << x << " is not equal with " << y;

        return 0;
    }
    </code>

    Without having to create a bool function?
    (Btw, why aren't the code tags working?)

    • Gejsi

      I was using my phone earlier so I couldn't see the formatting options there.
      Sorry about that, here is the proper formatting code:

      • Alex

        The goal of the example is to show a simple function that returns a boolean value, that's all. In reality, you probably wouldn't want to write such a trivial function -- but this foundation sets us up for writing more complex functions that you probably wouldn't want to add directly into main.

  • === QUOTE ===
    “I like asparagus”. Absolutely false (yuck!).
    === END QUOTE ===

    Speak for yourself :P

    (It's not that I "love" them, but I don't dislike them either) ;)

  • Hi. The code below builds, but when it's a prime number both the message to say it is and isn't is displayed. I had a look at the answer and I think this was a little naughty if you've only gone through the tutorials so far.  There has been no mention of using multiple else's.  So, at this point I will amend my code to see if adding elses instead of the if's gives the correct results.  Just to say, this is a fabulous resource, so big thumbs up to you Alex for making it available, it's awsome!

    (code)
    #include <iostream>
    #include <limits>

    // ask the user for a number

    int input_number()
    {
        std::cout << "Please input your first number: " << std::endl;
        int x;
        std::cin >> x;
        return x;
    }

    bool compare(int x, int y)
    {
        return x == y;
    }

    int main()
    {
        int x{ input_number()};
        
        if (compare(x, 2))
            std::cout << "This is a prime number" << std::endl;
        if (compare(x, 3))
        std::cout << "This is a prime number" << std::endl;
        if (compare(x, 5))
            std::cout << "This is a prime number" << std::endl;
        if (compare(x, 7))
            std::cout << "This is a prime number" << std::endl;
            else
            std::cout << "This is not a prime number" << std::endl;
        std::cin.clear(); // reset any error flags
        std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n'); // ignore any characters in the input buffer until we find an enter character
        std::cin.get(); // get one more char from the user
    return 0;
    }
    (/code)

  • Richard Ward

    Would it not be worth preferring to *always* use braces for ifs? Particularly in the wake of the Apple SSL bug a few years back.

    • Hi Richard!

      I strongly agree. It's easier to read and update and less prone to errors. People here have made the mistake of skipping braces, but indenting, multiple times, leading to problems.
      Still, some people like to leave them out.

  • Okorie Emmanuella

    Hi Nascardriver!
    Here's my own solution to the above quiz. Though, it doesn't quite work as it should.
    It says 2 is not a prime number. What did i do wrongly?

    thank you.

    • Hi!

      * Line 15: Initialize your variables with uniform initialization. You used copy initialization.
      * Line 4: Initialize your variables with uniform initialization.

      x % 1 is 0 for every number
      x % x is 0 for every number
      x % 2 is 1 for odd numbers

      So all you're doing is checking for odd numbers. 2 is even, so your code doesn't consider it a prime number.
      Have a peek at the modulus section in lesson 3.2.

      Note that you're not supposed to detect all prime numbers, just the 4 numbers mentioned in the task.

  • John D

    Hey guys! I'm having a bit of trouble - I've coded the first basic example, (with the if and else statement determining whether the input integers are equal), but the program finishes executing immediately following the second input, and the if/else output never displays. I remember an early lesson mentioning returning control to the user rather than ending the program altogether, but I can't seem to find my note on that, (and I'm not sure it even applies here).

    I thought it might be an error in code, so I simply pasted in the authors code to test that. But it ran just as mine did, ending abruptly at the second input without printing the results. Any help you guys can provide would be greatly appreciated!

  • Atte

    Hey,

    So while I tried to solve this code I made mine a little different. Is it ok or is the example solution better for any reason?

    • Hi Atte!

      * Line 11: Initialize your variables with uniform initialization.

      Your code doesn't work. Enable compiler warnings an fix them.
      The comma operator returns the value of the last expression. In your case, @isPrime will only return true of @x == 7.

  • Hannes Wadman

    Is this program okay or is it too inefficient? (This by the way is "Prime.cpp" and is called by main in my "learning.cpp" program.) Also fmod is as I understand it more or less % for floats I hope that's correct! Also how would one go about making numbers bigger than -(2^64)/2 and (2^64)/2-1(The shitty computer I'm on currently has double long as 8 bytes) and precision in floats longer than 16 digits? Thanks in advance!

    • Hi Hannes!

      > Also fmod is as I understand it more or less % for floats
      It is. If you have questions about what a standard function does, documentations are your friend.
      https://en.cppreference.com/w/cpp/numeric/math/fmod
      http://www.cplusplus.com/reference/cmath/fmod/
      Use @std::fmod instead of @fmod

      > Also how would one go about making numbers bigger
      There's no standard way of doing this. You'll have to write your own number type. You should be able to do this after bit-wise-operations and classes have been covered.

      > Is this program okay or is it too inefficient?
      * Initialize your variables with uniform initialization
      * Use double literals when calculating with doubles (1.0 instead of 1 and so on)
      * Perform simple checks first. Run line 13/17/23/27 before calling @fmod. Conditions in line 39/43 should be swapped.
      * Line 17 can be written as if (p < 0.0), since all numbers in (0.0, 1.0] have already been checked for.
      * Line 39: Calculate p/2.0 once. That way you don't have to calculate 2.0*n in every cycle.
      * Line 41: n += 2
      * Variable names should be descriptive. Use single-letter names for iterators only. "p" could be "dbUserInput", "n" should be "i".

      • Hannes Wadman

        Thank you very much! Just a few more follow up questions :)
        These will ask questions in order of appearance in the list you sent!

        * I'm assuming all the points in the list are things that could be more efficient, however I'm pretty sure the only variable I had to initialize(n) was initialized with uniform initialization in row 38. Should p also be initialized here just to make sure I avoid undefined behaviour or were you pointing out something else?

        * I looked up the links you sent me and it looks like a double fmod will always use two double floats. How did my code work with long double fmod(which I couldn't properly do before but I assume after reading the link it's just fmodl. Visual Studio seemed to make it into long double fmod for me in the code above though when I hover over it with my mouse) when I didn't define the literal as long double fmod? When I just write 2 and not 2l or 2f I'm going to assume it's automatically made into an int or a double, but the code seemed to work fine anyways. Why does this happen since we normally have to define the literals when assigning them to variables?

        * I'm assuming this is more efficient because we won't always have to make the "hard"/demanding calculations every time we run the code since we might be able to end the function before we get to that part if it's even, negative etc. I was just wondering if we assume one case is gonna be very uncommon in relation to the other cases e.g entering a negative number vs entering an even number, we should put the function calculating whether the number is before the one testing whether it's negative or not. Also even though entering a number like 1083 that is not negative, not a decimal, not even, not one or 0 is way more likely than entering a negative number I'm assuming we still put the function testing if the number is smaller than 1(which I'm gonna change to smaller than 0) since it's just so much less demanding than testing if it's divisible by 3, 5, 7 and so on. Is all of this correct? How would you order them?
        If I swap the conditions and let's say p = 20 and n = 3 it will just skip the while function go into if and if will fail and it will print p is prime even though it's not prime. I feel like I'm misunderstanding what you meant horribly but since you only said conditions I assume you didn't mean the while and if as well, but even then it won't work right?

        * I will make sure to do that! Will this improve performance slightly?

        * Will it remember that p / 2 has been calculated as well that p hasn't been changed and not calculate it again?

        * I will change this too, but I'm wondering if the change is more efficient or is it just "best practice" since it's more commonly used(assumption)?

        * I see I'm already falling into the pitfalls "I won't change this whatever let's just use random numbers" :). Well better to make mistakes sooner than later! Should n be i for any specific reason however?

        Thank you SO MUCH! I really appreciate you helping me even though you're under absolutely no obligation.

        • > Should p also be initialized
          Always initialize everything. This way you won't ever forget to initialize a variable that has to be initialized and your program will be in a well defined state at any point in time. If you're certain about what you're doing you can drop some initializations in favor of efficiency.

          > fmod
          Version (4) of @std::fmod on cppreference:

          @Arithmetic1 and @Arithmetic2 can be turn into any arithmetic type, because they are templates. Templates are covered later.

          > efficiency
          You got a point there. You have to weigh between how difficult it is to evaluate a condition and how likely it is to even get there.

          > it will just skip the while
          I was worried about my statement being ambiguous. I didn't mean swap the lines, but swap the conditions in each line.

          And the same for the if. Again, the reason being that the multiplication is faster than calling @std::fmod. And again, one could argue about likeliness of one condition failing before the other.

          > Will this improve performance slightly?
          Assuming your compiler didn't optimize your current version, yes.

          > Will it remember that p / 2 has been calculated
          It might, but you should make sure it does by introducing a temporary.

          > I'm wondering if the change is more efficient or is it just "best practice"
          There should be no difference after compilation. += is faster to read and easier to update (If you decide to rename the variable eg.).

          > Should n be i for any specific reason however?
          Single letter, because it's an iterator. 'i', because it's an int. If you have nested loops (Loop in a loop), one continues naming the next iterators alphabetically. Like one would do in maths. i -> j -> k ...

          > Thank you SO MUCH!
          You're welcome :-)

          • Hannes Wadman

            One last thing! I know I'm asking a lot of questions.
            By using 0.0 instead of 0 am I not taking up more space since one is an int(4 bytes on my system) and one is a double(8 bytes on my system)? Or will the templates take up the full 8 bytes anyways if it's a double fmod for example?

            • The int has the be promoted to a (long) double before any calculations can be performed with another (long) double.
              The problem with using ints where you want doubles is that, at some point, you'll forget to use a double when you have to. Always use the appropriate types and you won't run into this.

  • Anon

    Thanks =]

    • Hi Anon!

      * Line 2: Don't use "using namespace".
      * Line 6, 8, 18, 20: Initialize your variables with uniform initialization.
      * Line 6: @x cannot be divisible by anything bigger than (x / 2).
      * Line 8, 9 and 20, 21: Unnecessary temporary
      * Poor variable names. Variable names should be descriptive.

  • Hue Saki

    hey there/
    this works fine in mine code block

    int main()
    {
        bool b; // uninitialized variable
        std::cout << "Enter a boolean value: ";
        std::cin >> b;
            std::cout << "You entered: " << b;

        return 0;
    }

  • jeron

  • George

    Great lesson! I was wondering, how would the program in the quiz be written if one wanted to include all prime numbers and not just single digits?

    • You'd have to write an algorithm to either calculate prime numbers, or write an algorithm to detected weather or not a given number is prime, then walk through all numbers and print only those for which the algorithm decides that the number is prime.
      You'll learn how to do this in later lessons.

    • jeron

  • bbducky

    Just wanted to say that this quiz was really confusing.  I missed the "single integer" part and thought I needed to come up with a program that would tell you whether or not ANY number entered was prime, and after banging my head against the wall for like 30 minutes I just gave up lol.  Even after I realized the problem though,  I still struggled.  This is what I initially tried and I don't understand why it doesn't work if I write my main loop like this:

    Why do I need to create another bool called prime and then use that instead of just plugging isPrime directly?  If anyone could help explain that would be great as I'm super confused...

    • Hi bbducky!

      In line 5 you're calling @isPrime, passing the variable @x. @isPrime returns a boolean, which you're not storing anywhere, it is discarded.
      Line 7 will always be true, because functions are always non-null (You'll learn more about this later).

      * Line 2: Initialize your variables with uniform initialization
      * Line 10, 15 should be moved outside of the conditional blocks, because they are independent of the condition.

      References
      Lesson 1.4 - A first look at functions and return values

  • Hello!
    I figured out the issue. Posting the correct program below. I thought it was something to do with the (x == 2, 3, 5, 7). I went back to 2.1 and saw that each integer had to have a something attached.

    INCORRECT

    CORRECT

    • Hi Adrian!

      > CORRECT
      If you had read the compiler warnings or tested your code, you'd know that it is incorrect.
      The comma operator will execute all members, but it discards all values except the last one (x == 7). Your @isPrime function only returns true if @x is 7, false otherwise.
      Have a look at Alex' solution.

  • Dan

    Hi,

    Can you explain the reason behind return false;? I understand that it's meaning is to return a false value, but does the compiler know this as like an invisible else statement?

  • Hi Flux!

    Working, congrats, but

    * Line 10: Initialize your variables with uniform initialization
    * Line 14, 16, 18, 20: Don't repeat yourself, this is what the boolean mentioned in the quiz is for.

    Try to come up with a solution with less repeated code to make sure you understood booleans.

    • Flux

      Oh hi, I've seen you on lots of posts. It's an honor to have you reply. :) To celebrate, I've made the changes you noted and, as an added bonus, an attempt at input validation using just the tools covered up to 2.6

      • Good job!

        Two things,
        1. @isValid isn't used
        2. When you have a conditional statement which exceeds one line, wrap it in curly braces. (Line 18-22)

        • Flux

          Good eye, it surely was not used. That changed the amount of statements attached to that if, so hopefully I've formatted it correctly.

  • Flux

    Here's my less elegant, less readable nested solution.

Leave a Comment

Put all code inside code tags: [code]your code here[/code]