Thread: Problems with linked lists from *.dat

  1. #1
    Unregistered
    Guest

    Problems with linked lists from *.dat

    I'm trying to create a linked list from a standard data file that looks like this ...

    number TAB description TAB debit/credit TAB amount TAB date TAB balance END

    I'm getting a segmentation fault when I try to create the list, and I'm not sure why. I suspect it has something to do with the fact that I'm trying to read strings and floats off of one line, and I'm not sure how to accomplish that.

    Here's the code...

    #include<stdio.h>
    #include<stdlib.h>
    #include<string.h>

    struct checkingnode
    {
    char num[8] ;
    char comment[32] ;
    char deb_cred[8] ;
    float amt ;
    char date[12] ;
    float bal ;
    struct checkingnode *nextptr ;
    } ;

    typedef struct checkingnode Checking ;
    typedef Checking *checkptr ;

    void check_open( checkptr * ) ;

    int main()
    {

    checkptr firstptr = NULL ;

    check_open( &firstptr ) ;

    }

    /*****************************************
    Function: check_open
    Purpose: Opens the checking.dat file and
    creates the checking linked list.
    *****************************************/
    void check_open( checkptr *sptr)
    {

    FILE *ptrReadDat ;
    char NewLine[256] = {'\0'} ;
    checkptr curptr, newptr ;

    ptrReadDat = fopen( "checking.dat", "r" ) ;
    curptr = *sptr ;
    newptr = NULL ;
    curptr->nextptr = newptr ;

    if ( ptrReadDat == NULL )
    printf( "\nFile could not be opened.\n" ) ;

    else
    {
    fscanf( ptrReadDat, "%s\t%s\t%s\t%.2f\t%s\t%.2f\n", curptr->num, curptr->comment,
    curptr->deb_cred, curptr->amt, curptr->date, curptr->bal ) ;
    newptr = malloc( sizeof( Checking ) ) ;
    curptr->nextptr = newptr ;
    curptr = newptr ;
    newptr = NULL ;
    }

    fclose( ptrReadDat ) ;
    }

    What should I do to fix this?

    Thanks for any help!

  2. #2
    End Of Line Hammer's Avatar
    Join Date
    Apr 2002
    Posts
    6,231
    The problem is that you are trying to use a pointer before it has been assigned an address. In other words, it's NULL.

    This is because the variable you pass to check_open is just a pointer, that hasn't been assigned yet. You then copy the value of this pointer (NULL) to a local variable, and try to use it in the fscanf call.

    The prog actually terminates on line
    curptr->nextptr = newptr ;
    because curptr is NULL.

    In order to get around this, I'd suggest you use a temporary struct to load the data into, then once you are happy the read was good, proceed to malloc up some memory for the data, and assign the pointer the return from malloc. Then copy in the data from the temporary struct to the new memory area. (This is just one way of doing it, you will find other methods if you look around).

    You could still use the pointer method you have already, but you would need to malloc memory before trying to use the pointer. In this case though, if the read of the data fails, you wasted time malloc'ing memory that'd you'd have to free up straight away.

    There's plenty of examples of link list code about here. If you get stuck though, post back here with your changes and we'll have another go.
    When all else fails, read the instructions.
    If you're posting code, use code tags: [code] /* insert code here */ [/code]

  3. #3
    End Of Line Hammer's Avatar
    Join Date
    Apr 2002
    Posts
    6,231
    This is my version, based on your original code:
    Code:
    #include<stdio.h>
    #include<stdlib.h>
    #include<string.h>
    
    struct checkingnode
    {
    	char num[8] ;
    	char comment[32] ;
    	char deb_cred[8] ;
    	float amt ;
    	char date[12] ;
    	float bal ;
    	struct checkingnode *nextptr ;
    } ;
    
    typedef struct checkingnode Checking ;
    typedef Checking *checkptr ;
    
    void check_open( checkptr * ) ;
    
    int main(void)
    {
    	checkptr firstptr = NULL, tmpptr;
    
    	check_open( &firstptr ) ;
    	
    	tmpptr = firstptr;
    
    	// print the list to prove it worked.	
    	while (tmpptr)
    	{
    		printf("%s %s %.2f\n", tmpptr->num, tmpptr->comment, tmpptr->amt);
    		tmpptr = tmpptr->nextptr;
    	}
    	
    	// next job, write function to free all nodes in the list!
    	return (0);
    }
    
    /*****************************************
    Function: check_open
    Purpose: Opens the checking.dat file and
    creates the checking linked list.
    *****************************************/
    void check_open( checkptr *sptr)
    {
    	FILE *ptrReadDat ;
    	char buffer[200];
    	checkptr curptr = NULL, newptr;
    	Checking tmpNode;
    
    	if ((ptrReadDat = fopen( "checking.dat", "r" )) == NULL)
    	{
    		printf( "\nFile could not be opened.\n" ) ;
    		return;
    	}
    	
    	while (fgets(buffer, 200, ptrReadDat))	// read a line
    	{	
    		// sscanf is lame, 'cos it can't handle input errors.
    		// Also, strings are terminated when a white space character is read (eg space).
    		// Search the board for better ways of doing this type of thing.
    		if (sscanf( buffer, "%s\t%s\t%s\t%f\t%s\t%f\n", tmpNode.num, tmpNode.comment,
    			tmpNode.deb_cred, &tmpNode.amt, tmpNode.date, &tmpNode.bal ) == 6)
    		{	// line split up and stored into temp struct OK, so proceed
    			
    			if ((newptr = malloc( sizeof( Checking ) )) == NULL)
    			{	// malloc up some memory
    				perror("out of memory");
    				fclose( ptrReadDat );
    				return;  // do something better here
    			}
    			*newptr = tmpNode;	// copy the tmp struct to the new memory
    			if (curptr == NULL)
    			{	// if first time...
    				curptr = newptr;	//  pointer to new memory
    				*sptr = curptr;		//	also update the calling pointer (from function arg)
    			}
    			else
    			{	// pointer already been used, so ...
    				curptr->nextptr = newptr;	//	make the link from one node to the next
    				curptr = newptr;			//	move the pointer to the next node
    			}
    			curptr->nextptr = NULL;		// force the new nodes nextptr to NULL to prevent errors.
    		}
    	}
    	fclose(ptrReadDat);
    }
    When all else fails, read the instructions.
    If you're posting code, use code tags: [code] /* insert code here */ [/code]

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. about linked lists
    By armin_miewes in forum C Programming
    Replies: 4
    Last Post: 01-08-2004, 11:17 AM
  2. Implementing a linked list, some problems
    By EvBladeRunnervE in forum C++ Programming
    Replies: 7
    Last Post: 12-12-2003, 09:07 AM
  3. Questions on Linked Lists
    By Weng in forum C++ Programming
    Replies: 1
    Last Post: 11-29-2003, 01:17 AM
  4. Linked Lists Integer addition ? HELP Please??
    By green_eel in forum C Programming
    Replies: 3
    Last Post: 03-12-2003, 04:36 PM
  5. Replies: 1
    Last Post: 03-21-2002, 06:10 PM