0

I just started messing around with C++ but I am stuck. Any help would be much appreciated.

I want to change the value of gameState from true to false by passing in another function, however, my thought process seems to be incorrect:

#include <iostream>
#include <vector>
#include <string>
#include <fstream>
using namespace std;

void changeState(bool gameState){
  string answer;
  cout << "End game? Y/N" << endl;
  cin >> answer;

  if(answer == "Y"){
    gameState = false;
  } else if (answer == "N"){
    gameState = true;
  }    
}

void gameLoop(){
  bool gameState = true;
  while(gameState == true){
    cout << "Game is being played" << endl;
    changeState(gameState);
  }    
}

int main(){    
  gameLoop();  
  return 0;
}
Rama
  • 3,222
  • 2
  • 11
  • 26
Ayaz Uddin
  • 105
  • 2
  • 13
  • 4
    Pass by reference or pointer. – sharyex Dec 05 '16 at 20:18
  • Possible duplicate of [What's the difference between passing by reference vs. passing by value?](http://stackoverflow.com/questions/373419/whats-the-difference-between-passing-by-reference-vs-passing-by-value) – user4581301 Dec 05 '16 at 20:18
  • Alternatively, you could make gameState a global variable (i.e. move the "bool gameState = true;" line up, so that it appears above the "void changeState(bool gameState){" line) – Jeremy Friesner Dec 05 '16 at 20:19
  • 1
    There are several ways: reference parameter, return a value (input value of `gameState` is not used...), global (ugh!), object with game state (better), everything is inside game object (even better). – crashmstr Dec 05 '16 at 20:20
  • 2
    Why not just return the new state from the function? – molbdnilo Dec 05 '16 at 20:20
  • Why are you passing `gameState`'s original vaolue to `changeState`? – David Schwartz Dec 05 '16 at 20:30
  • Personally, if you're not going with a stateful object, I'd go with returning the new value, not accepting an argument by mutable reference. Mutable references always feel worrisome to me, since there is no obvious indicator that reference semantics are in use at the caller side; `const` references don't have it either, but at least there is no spooky action at a distance, it largely acts the same as passing by value, just without the copy overhead. – ShadowRanger Dec 05 '16 at 20:30

3 Answers3

2

By default, function parameters are passed "by value" to c/c++ functions. This means that the function has its own local copy of the gamestate variable that is initialized to the value given by the caller.

You have 2 possibilities: to change the function to take a reference to the variable or to take a pointer to the variable instead.

A function taking a reference would look like this:

void ChangeState (bool &gameState){
   gameState=false;
}

Using a pointer would look like this:

void ChangeState (bool *gameState){
   *gameState=false;
}

.... ChangeState (&gameState);

Using a reference can be seen as more convenient as the syntax and the use of the local variable is not changed. On the other hand, using a pointer forces the caller to use the & to take the address of the variable, so everybody looking at the function call is made aware that the value may be changed inside the function.

Sami Sallinen
  • 3,203
  • 12
  • 16
1

In c++ when you pass an argument to a function it generally is passed a copy of that value, that means it is just a copy of what that variable contains, and isn't that variable. In order to create an output parameter a simple solution is to pass by reference or pointer.

I will show the reference version:

void changeState(bool& gameState){
  string answer;
  cout << "End game? Y/N" << endl;
  cin >> answer;

  if(answer == "Y"){
    gameState = false;
  } else if (answer == "N"){
    gameState = true;
  }
}

The code is the exact same the only difference is the & after the bool inside the parameter list.

This tutorial will go into more detail: http://www.cplusplus.com/doc/tutorial/functions/

Also just a fyi, a reference or pointer depending on the OS, could be 4 bytes, where your bool is typically 1 byte, just returning a bool value would take less memory then passing by reference.

AresCaelum
  • 1,558
  • 1
  • 13
  • 18
1

Return the gameState varible passed by value, there is no need to pass by reference or pointer in your code, this could lead to hide behavior,

#include <iostream>
#include <vector>
#include <string>
#include <fstream>
using namespace std;

bool changeState(bool gameState){
  string answer;
  cout << "End game? Y/N" << endl;
  cin >> answer;

  if(answer == "Y"){
    gameState = false;
  } else if (answer == "N"){
    gameState = true;
  }  
  return gameState; 
}

void gameLoop(){
  bool gameState = true;
  while(gameState == true){
    cout << "Game is being played" << endl;
    gameState = changeState(gameState);
  }    
}

int main(){    
  gameLoop();  
  return 0;
}
Rama
  • 3,222
  • 2
  • 11
  • 26