Search code examples
c++control-flow

if statement followed by return 0


I have some code like:

#include <iostream>
#include <string>

int main() {
    std::string question;

    std::getline(std::cin, question);
    
    if (question == "yes") {
        std::cout << "Let's rock and roll!" << std::endl;
        return 0; // This line
    } if (question == "no") {
        std::cout << "Too bad then..." << std::endl;   
    } else {
        std::cout << "What do you mean by that?" << std::endl;
    }
    return 0;
}

If I don't write the commented return 0 line and input yes, the output is Let's rock and roll! followed by What do you mean by that?. It should only output Let's rock and roll!.

But I don't need to put return 0 in the if (question=="no"){...} block. If I input no, the output is just Too bad then....

Why do I need the return 0 in the first case, but not the second?


Solution

  • Control flow is your issue here:

         if(question == "yes"){
            std::cout<<"Lets rock and roll!"<<std::endl;
            return 0;
         }if (question == "no"){
            std::cout<<"Too bad then..."<<std::endl;   
         } else{
            std::cout<<"What do you mean by that?"<<std::endl;
         }
    

    Let's format this a bit better by surrounding if/else statements/blocks with newlines and adding some whitespace around operators. Your compiler doesn't care (much) about whitespace when compiling code, but it conveys a lot of meaning to humans reading code, and poor formatting can convey a meaning that isn't reflected by the actual code.

         if (question == "yes") {
            std::cout << "Lets rock and roll!" << std::endl;
            return 0;
         }
    
         if (question == "no") {
            std::cout << "Too bad then..." << std::endl;   
         } 
         else {
            std::cout << "What do you mean by that?" << std::endl;
         }
    

    These are two different conditionals. The first one being triggered does not stop the second if/else from being evaluated. In fact, if question equals "yes" then it cannot equal "no" so the else clause in the second if/else must be executed.

    By including return 0; in the first conditional block, the function exits immediately, thus skipping everything after it. The second if/else is not evaluated and "What do you mean by that?" is never printed.

    You likely wanted this to be a single if/else. Now only one of these blocks will be executed. Because an else is included as a catch-all in the event none of the previous conditions were met, it is guaranteed one branch will be executed.

         if (question == "yes") {
            std::cout << "Lets rock and roll!" << std::endl;
         }
         else if (question == "no") {
            std::cout << "Too bad then..." << std::endl;   
         } 
         else {
            std::cout << "What do you mean by that?" << std::endl;
         }
    

    An alternative approach entirely is to use a mapping of a string input to a response. This scales better to a larger assortment of inputs/responses.

    #include <iostream>
    #include <string>
    #include <unordered_map>
    
    int main() {
        const std::unordered_map<std::string, std::string> map = {
            {"yes", "Lets rock and roll!"},
            {"no", "Too bad then..."}
        };
        std::string input;
    
        std::getline(std::cin, input);
        
        try {
            std::cout << map.at(input) << '\n';
        }
        catch (std::out_of_range) {
            std::cout << "What do you mean by that?\n";
        }
    }