c++if-statementsdl-2tinyxml2

C++ Why can't I get into an if condition if the statement is true?


I made a for loop in the constructor that goes through XML elements of bricks and creates the brick depending on what the Id is.

I even checked typeid in case mId wasnt a char but it's const char*. The std::cout << "Made it in"; never triggers. Here is the code:

Brick::Brick(int rowSpacing, int columnSpacing, const char* Id, SDL_Renderer* renderer)
{
    mDoc = new XMLDocument();
    mDoc->LoadFile("Breakout.xml");

    // Go through every "BrickType" element in the XML file
    dataElement = mDoc->FirstChildElement("Level")->FirstChildElement("BrickTypes");

    for (XMLElement* brickElement = dataElement->FirstChildElement("BrickType");
        brickElement != NULL; brickElement = brickElement->NextSiblingElement())
    {
        std::cout << typeid(brickElement->FirstChildElement("Id")->GetText()).name();
        std::cout << typeid(Id).name();

        if (brickElement->FirstChildElement("Id")->GetText() == Id) {
            std::cout << "Made it in";

            mId = brickElement->FirstChildElement("Id")->GetText();

            std::stringstream hp(brickElement->FirstChildElement("HitPoints")->GetText());
            hp >> mHitPoints;

            std::stringstream bs(brickElement->FirstChildElement("BreakScore")->GetText());
            bs >> mBreakScore;

            mTexture = IMG_LoadTexture(renderer, brickElement->FirstChildElement("Texture")->GetText());            
        }
    }

    mCurrentHp = mHitPoints;

    mIsHit = false;

    rect = { rowSpacing, columnSpacing, mBrickWidth, mBrickHeight };
}

Instead of the Id in if (brickElement->FirstChildElement("Id")->GetText() == Id) i tried hard coding "S" as one of the brick Ids is "S", like this if (brickElement->FirstChildElement("Id")->GetText() == "S"), but it still doesn't want to get into an if condition, I don't understand why.


Solution

  • C Strings are character arrays and not first-class datatypes in C++ (is C as it happens(. As such you cannot use comparison operators on them. Semantically you are comparing the value of two pointers, not the content of two strings.

    To that end, you either need a C-String comparison:

    if( strcmp(brickElement->FirstChildElement("Id")->GetText(), 
               Id) == 0 ) ...
    

    or use the C++ std::string comparison:

    if( std::string(brickElement->FirstChildElement("Id")->GetText()) ==
        std::string( Id ) ) ...
    

    The std::string class overloaded the == operator (and others) so that it compares the content. Constructing a std::string just to perform a comparison is somewhat heavyweight, but in other circumstances, you might do well to use std::string in preference to C-Strings in any case.