Thread: pointer always NULL?

  1. #1
    Seeking motivation... endo's Avatar
    Join Date
    May 2002
    Posts
    537

    pointer always NULL?

    I am trying to create a Competitor-derived object from user input. The code below is where this should happen, the getCompetitorData(...) function creates the object but when control is returned to the calling block of code the pointer is equal to NULL again. Why is this? I cant see any problems in the code so this is my last resort before redoing the whole program

    Code:
    	Competitor* newCompetitor = NULL;
    
    	switch( option )
    	{
    	case 1:
    		if( ! getCompetitorData( comp, newCompetitor ) )
    		{
    			cerr << "competitor not created";
    			exit( 0 );
    		}
    		if( newCompetitor == NULL )
    		{
    			cerr << "newCompetitor==NULL, editMenu()";		//why should it be NULL??
    			Sleep( 5000 );
    			exit( 0 );
    		}
    		comp.addCompetitor( newCompetitor );
    
    		if( newCompetitor != NULL )
    			delete newCompetitor;
    
    		newCompetitor = NULL;
    		system( "cls" );
    		cout << "\nThis competition has " << comp.countRecords( ) << " entries so far" << endl;
    
    		break;
    
    	default:
    		break;
    	}
    //getCmpetitorData(...)
    Code:
    bool getCompetitorData( Competition& comp, Competitor* empty)
    {
    	system( "cls" );
    	char first[ MAX ];
    	cout << "\nEnter first name : ";
    	cin.getline( first, MAX, '\n' );
    
    	char last[ MAX ];
    	cout << "\nEnter last name : ";
    	cin.getline( last, MAX, '\n' );
    
    	int age;
    	cout << "\nEnter age : ";
    	cin >> age;
    	cin.ignore( 80, '\n' );
    
    	if( !cin.good( ) )
    	{
    		cerr << "Bad input fool!" << endl;
    		return false;
    	}
    
    	char sex;
    	cout << "\nSex ( M or F ): ";
    	cin >> sex;
    	cin.ignore( 80, '\n' );
    
    	SEX enumSex;
    
    	if( sex != 'm' && sex != 'M' && sex != 'f' && sex != 'F'  )
    	{
    		cerr << "Bad input fool!" << endl;
    		return false;
    	}
    	else
    	{
    			(sex == 'm' || sex == 'M' ) ? enumSex = MALE : enumSex = FEMALE;
    	}
    
    
    	char school[ MAX ];
    	cout << "\nEnter name of Taekwon-do school : ";
    	cin.getline( school, MAX, '\n' );
    
    
    	char grade;
    	cout << "\nEnter competitors grade ( Y, G, B, R, 1, 2, 3 or 4 ) : ";
    	cin >> grade;
    
    	GRADE enumGrade;
    
    	switch( grade )
    	{
    	case 'y':
    	case 'Y':
    		enumGrade = YELLOW;
    		break;
    	case 'g':
    	case 'G':
    		enumGrade = GREEN;
    		break;
    	case 'b':
    	case 'B':
    		enumGrade = BLUE;
    		break;
    	case 'r':
    	case 'R':
    		enumGrade = RED;
    	case '1':
    		enumGrade = FIRST;
    		break;
    	case '2':
    		enumGrade = SECOND;
    	case '3':
    		enumGrade = THIRD;
    	case '4':
    		enumGrade = FOURTH;
    		break;
    
    	default:
    		cerr << "Bad input fool!!" << endl;
    		return false;
    	}
    
    	int heightOrWeight;
    
    	cout << ( age < 18 ? "\nEnter height ( cm ): " : "\nEnter weight ( kg ) : " );
    	cin >> heightOrWeight;
    	cin.ignore( 80, '\n' );
    
    	if( !cin.good( ) )
    	{
    		cerr << "Bad input fool!" << endl;
    		return false;
    	}
    
    	char spar, patterns, power, special;
    	cout << "\nEvents entered - y or n: " << endl;
    
    	cout << "Sparring : ";
    	cin.get( spar );
    	cin.ignore( 80, '\n' );
    	if( checkYesNoInput( spar ) )
    		return false;
    
    	cout << "\nPatterns : ";
    	cin.get( patterns );
    	cin.ignore( 80, '\n' );
    	if( checkYesNoInput( patterns ) )
    		return false;
    
    	cout << "\nPower : ";
    	cin.get( power );
    	cin.ignore( 80, '\n' );
    	if( checkYesNoInput( power ) )
    		return false;
    
    	cout << "\nSpecial technique : ";
    	cin.get( special );
    	cin.ignore( 80, '\n' );
    	if( checkYesNoInput( special ) )
    		return false;
    
    	if( age >= 18 )
    	{
    		try
    		{
    			empty = new Adult( first, last, age, enumGrade, enumSex, school, 
    				checkYesOrNo( spar ), checkYesOrNo( patterns ), checkYesOrNo( power ), checkYesOrNo( special ), heightOrWeight );
    		}catch( bad_alloc ex )
    		{
    			cerr << "bad_alloc caught, Adult not created" << endl;
    		}
    	}
    	else
    	{
    		try
    		{
    			empty = new Child( first, last, age, enumGrade, enumSex, school, 
    				checkYesOrNo( spar ), checkYesOrNo( patterns ), checkYesOrNo( power ), checkYesOrNo( special ), heightOrWeight );
    		}catch( bad_alloc ex )
    		{
    			cerr << "bad_alloc caught, Child not created" << endl;
    		}
    	}
    
    	return true;
    }
    When is gets to the addCompetitor(...) the pointer is NULL again.

    tia
    Couldn't think of anything interesting, cool or funny - sorry.

  2. #2
    Me want cookie! Monster's Avatar
    Join Date
    Dec 2001
    Posts
    680
    The reason why it's not working is that you pass a pointer to NULL. You need to pass the address of that pointer so the new pointer (allocated with new) can be stored in that address. Try something like this:

    Code:
    getCompetitorData( comp, &newCompetitor )
    ...
    ...
    bool getCompetitorData( Competition& comp, Competitor **empty)
    ...
    *empty = new Adult( first, last, age, enumGrade, ...

  3. #3
    Code Goddess Prelude's Avatar
    Join Date
    Sep 2001
    Posts
    9,897
    >Why is this?
    Pointers are just like any other variable, if you want to change what the pointer points to in another function then you must pass it by its address:
    Code:
    #include <iostream>
    
    // When defined, the allocation will not work in main.
    #define FAIL_CHECK
    
    int allocMem1 ( int *empty )
    {
      empty = new int;
      if ( empty == NULL )
        return 2;
      return 1;
    }
    
    int allocMem2 ( int **empty )
    {
      *empty = new int;
      if ( *empty == NULL )
        return 2;
      return 1;
    }
    
    int main()
    {
      int *var = NULL;
    #ifdef FAIL_CHECK
      if ( allocMem1 ( var ) == 1 ) {
    #else
      if ( allocMem2 ( &var ) == 1 ) {
    #endif
        if ( var == NULL )
          std::cout<<"It didn't work\n";
        else
          std::cout<<"It did work!\n";
      }
      return 0;
    }
    Try running the program with FAIL_CHECK defined and then run it with FAIL_CHECK commented out to see the difference between allocMem1 and allocMem2.

    -Prelude
    My best code is written with the delete key.

  4. #4
    Registered User
    Join Date
    Oct 2001
    Posts
    2,934
    Or:
    bool getCompetitorData( Competition& comp, Competitor* &empty)

  5. #5
    Registered User The Dog's Avatar
    Join Date
    May 2002
    Location
    Cape Town
    Posts
    788
    What you could also do is to return the pointer and then assign it.
    You would then also do some tests to check if the function worked properly so to speak.

    Code:
    Competitor* getCompetitorData( Competition& comp, Competitor* empty)

  6. #6
    Seeking motivation... endo's Avatar
    Join Date
    May 2002
    Posts
    537
    Thanks all, that should keep me going for a while....
    Couldn't think of anything interesting, cool or funny - sorry.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. addrinfo Structure Not Working
    By pobri19 in forum Networking/Device Communication
    Replies: 9
    Last Post: 10-22-2008, 10:07 AM
  2. Replies: 7
    Last Post: 06-16-2006, 09:23 PM
  3. Button handler
    By Nephiroth in forum Windows Programming
    Replies: 8
    Last Post: 03-12-2006, 06:23 AM
  4. Why am I getting these errors??
    By maxthecat in forum Windows Programming
    Replies: 3
    Last Post: 02-03-2006, 01:00 PM
  5. Quick question about SIGSEGV
    By Cikotic in forum C Programming
    Replies: 30
    Last Post: 07-01-2004, 07:48 PM