I’m trying to solve a CodeWars exercise in wich I have to evaluate the winner between two fighters.
The function returns an std:sting.
The issue I’m having in the page says:
"warning: control may reach end of non-void function [-Wreturn-type]
runtime error: execution reached the end of a value-returning function without returning a value"
At the two initial if’s.
However, when I compile on my IDE, there is no such warning.
Any clues about what can be causing the issue?
std::string declareWinner(Fighter* fighter1, Fighter* fighter2, std::string firstAttacker) {
//initialize stats to 0
int firstAttackerHealth{0}, secondAttackerHealth{0}, secondAttackerDamage{0}, firstAttackerDamage{0};
std::string secondAttacker;
//decide who is the first attacker and assign stats values
if (fighter1->getName() == firstAttacker) {
firstAttacker =fighter1->getName();
firstAttackerHealth = fighter1->getHealth();
firstAttackerDamage = fighter1->getDamagePerAttack();
secondAttacker = fighter2->getName();
secondAttackerHealth = fighter2->getHealth();
secondAttackerDamage = fighter2->getDamagePerAttack();
}
else if(fighter2->getName() == firstAttacker) {
firstAttacker = fighter2->getName();
firstAttackerHealth = fighter2->getHealth();
firstAttackerDamage = fighter2->getDamagePerAttack();
secondAttacker = fighter1->getName();
secondAttackerHealth = fighter1->getHealth();
secondAttackerDamage = fighter1->getDamagePerAttack();
}
cout << firstAttacker << " vs " << secondAttacker << '\n';
cout << firstAttacker << " has a total of " << firstAttackerHealth << " points of health '\n";
cout << secondAttacker << " has a total of " << secondAttackerHealth << " points of health '\n";
cout << "Fight!'\n'";
//start the combat only if both health values are above 0
while (firstAttackerHealth > 0 && secondAttackerHealth > 0) {
//check fot attacker health, if greater than 0, then they can damage the opponent
if (firstAttackerHealth > 0) {
std::cout << firstAttacker << " punches for " << firstAttackerDamage << '\n';
secondAttackerHealth-=firstAttackerDamage;
std::cout << secondAttacker << "'s life is now " << secondAttackerHealth << '\n';
}
if (secondAttackerHealth > 0) {
std::cout << secondAttacker << " punches for " << secondAttackerDamage << '\n';
firstAttackerHealth -= secondAttackerDamage;
std::cout << firstAttacker << "'s life is now " << firstAttackerHealth << '\n';
}
// check for the first attacker with health less than 0 and returns the
// other attacker
if (firstAttackerHealth <= 0) {
std::cout << firstAttacker << "' health is: " << firstAttackerHealth << " , "
<< firstAttacker << " has lost '\n'";
return secondAttacker;
}
else if (secondAttackerHealth <= 0)
{
std::cout << secondAttacker << "' health is: " << secondAttackerHealth << " , "
<< secondAttacker << " has lost '\n'";
return firstAttacker;
}
}
}
>Solution :
The problem is that the compiler does not analyze the code deep enough, to understand the connection between your while-statement and the if-else-if at the bottom. An easy way to fix this is to change your while statement to
while (true) {
thus making it clear that the loop can only be exited with a break or return.
Another possiblity is to move the return statement outside of the loop:
std::string rv;
while (firstAttackerHealth > 0 && secondAttackerHealth > 0) {
//check fot attacker health, if greater than 0, then they can damage the opponent
if (firstAttackerHealth > 0) {
std::cout << firstAttacker << " punches for " << firstAttackerDamage << '\n';
secondAttackerHealth-=firstAttackerDamage;
std::cout << secondAttacker << "'s life is now " << secondAttackerHealth << '\n';
}
if (secondAttackerHealth > 0) {
std::cout << secondAttacker << " punches for " << secondAttackerDamage << '\n';
firstAttackerHealth -= secondAttackerDamage;
std::cout << firstAttacker << "'s life is now " << firstAttackerHealth << '\n';
}
// check for the first attacker with health less than 0 and returns the
// other attacker
if (firstAttackerHealth <= 0) {
std::cout << firstAttacker << "' health is: " << firstAttackerHealth << " , "
<< firstAttacker << " has lost '\n'";
rv = secondAttacker;
break;
}
else if (secondAttackerHealth <= 0)
{
std::cout << secondAttacker << "' health is: " << secondAttackerHealth << " , "
<< secondAttacker << " has lost '\n'";
rv = firstAttacker;
break;
}
}
return rv;
The break-statements are not really necessary as the while condition will become false anyways, if some of this code is executed.