Thread: Dynamic Array of Structs Help

  1. #1
    Registered User
    Join Date
    Apr 2006
    Posts
    2

    Dynamic Array of Structs Help

    I need to tabulate a word count from an external file using a dynamic array of pointers to structures.

    I can compile fine, but it screws up in my add function, during this line:

    strcpy((*nptr)[*t].new_word, *until_space);
    (*nptr)[*t].count = 1;

    Here is my full program for reference:

    Code:
    #include <iostream>
    #include <iomanip>
    #include <fstream>
    #include <ctype.h>
    using namespace std;
    
    struct Word
    {
    	char new_word[50];
    	int count;
    };
    
    #define MAX_FILENAME 255
    
    void program();
    void run(char in_file[MAX_FILENAME], char out_file[MAX_FILENAME]);
    void check(Word *** ptr, char ** until_space, int t, int *d);
    void add(Word *** ptr, char ** until_space, int *t);
    
    void main()
    {
    	program();
    }
    
    void program()
    {
    	char in_file[MAX_FILENAME];
    	char out_file[MAX_FILENAME];
    
    	cout << "Enter the name of the input file ->";
    	cin.ignore(cin.rdbuf() -> in_avail());
                    cin.getline(in_file, 256);
    
    	cout << "Enter the name of the output file ->";
    	cin.ignore(cin.rdbuf() -> in_avail());
    	cin.getline(out_file, 256);
    
    	run(in_file, out_file);
    }
    
    void run(char in_file[MAX_FILENAME], char out_file[MAX_FILENAME])
    {
    	Word ** ptr = new Word*[];
    	int t(0);	// Total unique words
    	int d;		// Descision
    	char * until_space = new char[256];
    
    	ifstream fin(in_file);
    	ofstream fout(out_file);
    
    	if(fin.fail() || fout.fail())
    		cout << "Error opening files" << endl;
    
    	else
    	{
    		do
    		{
    			d = 0;
    			//READ IN NEXT WORD
    			fin >> until_space;
    
    			check(&ptr, &until_space, t, &d);
    			if(d == 0)
    			            add(&ptr, &until_space, &t);
    
    		}while(!fin.eof());
    
    		for(int l(0); l < t; l++)
            	                           fout << ptr[l]->count << " " << ptr[l]->new_word << endl;
    
    		fin.close();
    		fout.close();
    	}
    	delete [] ptr;
    }
    
    void check(Word *** ptr, char ** until_space, int t, int *d)
    {
    	int f(0);	// Found douplicate
    	int s;		// Sting length
    
    	s = strlen(*until_space);
    	//TAKE ANY PUNCTUATION OFF
    	for(int p(0); p < s; p++)
    		if( ispunct( (*until_space)[p] ) )
    			(*until_space)[p] = '\0';		
    
    	s = strlen(*until_space);
    	//CONVERT TO LOWER CASE
    	for(int l(0); l < s; l++)
    	               (*until_space)[l] = tolower( (*until_space)[l] );
    
    	if( isdigit( (*until_space)[0] ))
    	;
    	else
    	{
            //COMPARE AGAINST ALREADY HAVE. ADD 1 IF DUPLICATE
    		for(int i(0); i < t; i++)
    		{
    			if(strcmp (*until_space, (*ptr)[i]->new_word) == 0)
    			{
    			    (*ptr)[i]->count += 1;
    				*d = 1;
    			}
    		}
    	}
    }
    
    void add(Word *** ptr, char ** until_space, int *t)
    {
    	Word ** nptr = new Word*[*t + 1];
    	for(int n(0); n < *t; n++)
    	{
    		strcpy((*nptr)[n].new_word, (*ptr)[n]->new_word);
    		(*nptr)[n].count = (*ptr)[n]->count;
    	}
    
    ::GLITCHES ON THIS NEXT LINE::
    	strcpy((*nptr)[*t].new_word, *until_space);
    	(*nptr)[*t].count = 1;
    
    	delete *ptr;
    
    	*ptr = new Word*[*t + 1];
    
    	for(int c(0); c < *t + 1; c++)
    	{
    		strcpy((*ptr)[c]->new_word, (*nptr)[c].new_word);
    		(*ptr)[c]->count = (*nptr)[c].count;
    	}
    
    	*t++;
    		
    	delete nptr;
    }
    Thank you in advance for the help.
    P.S. If there is an other glitches that you can see, please let me know

  2. #2
    Registered User
    Join Date
    Mar 2002
    Posts
    1,595
    void main() is not standard. It may work with some compilers and not in others. You would be better off using int main(). If your compiler uses namespaces it will surely use int main() as well.

    IMO it is preferable to use const int rather than #define

    To pass a char array from one function to another and have the changes made in the called function be available in the calling funciton you just need to send the char array, not a pointer to a char array. The same holds for two dimensional char arrays.

    In the following:

    Word ** ptr = new Word*[];

    each Word has a data member that is an array of 50 char. Each Word therefore can contain a single string. Therefore to get a table of strings you just need an array of Word. To do that with dynamic memory, you only need a single pointer, but you do need to specify how many Words you want to be able to hold--the value need not be a const, but it does need to be valid:

    int x = //value obtained from somewhere
    Word * ptr = new Word[x];
    You're only born perfect.

  3. #3
    carry on JaWiB's Avatar
    Join Date
    Feb 2003
    Location
    Seattle, WA
    Posts
    1,972
    There's definitely way too many *s in that program. Have you considered using the std::string class instead of char arrays?
    "Think not but that I know these things; or think
    I know them not: not therefore am I short
    Of knowing what I ought."
    -John Milton, Paradise Regained (1671)

    "Work hard and it might happen."
    -XSquared

  4. #4
    Registered User
    Join Date
    Apr 2006
    Posts
    2
    Thank you both for the suggestions. I walked back through and (as you both pointed out) I was stepping one to far in on my indirection. I removed it and the program works great!

    Thanks again

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Dynamic Array Allocation function
    By P4R4N01D in forum C++ Programming
    Replies: 6
    Last Post: 05-15-2009, 02:04 AM
  2. Dynamic Array of Structs help
    By fairguynova in forum C++ Programming
    Replies: 5
    Last Post: 02-04-2009, 11:20 PM
  3. Dynamic Mutli dimensional Array question.
    By fatdunky in forum C Programming
    Replies: 6
    Last Post: 02-22-2006, 07:07 PM
  4. Dynamic Array Resizing
    By dld333 in forum C++ Programming
    Replies: 13
    Last Post: 11-04-2005, 12:13 AM
  5. Quick question about SIGSEGV
    By Cikotic in forum C Programming
    Replies: 30
    Last Post: 07-01-2004, 07:48 PM