Hi,
The following code I've been working on (as hobbyist) compiles okay, buy at runtime it fails to output the dates that it is supposed to extract from a csv file. I've been staring at this forever and no progress.

I am thinking that the problem occurs before the date verification function, because when the program gets to cout << "This is the first date in the database" and cout << dataArray[0].date << endl, it does not output the date. This means that the first element in the array is empty, which means that the array did not populate for some reason.

Would appreciate any suggestions to identify the problem.

Thanks
TR

// Dataprep.cpp : Defines the entry point for the console application

#include "stdafx.h"
#include <vector>
#include <fstream>
#include <iostream>
#include <string> 
#include <sstream>
#include <math.h>
#include <cstring>
using namespace std;
int NumLines;
void Error (int);
int Open_Price_Data_File (char* filename);
struct Bar* Define_Array (const char*);
void Parse_Output_To_File (struct Bar* dataArray, const char*);
void Date_Verification ();
void ExitScreen ();



//Structure Declaration and Array Initialization 
       struct Bar
       {
               string date;              // date
               double open;              // opening price
               double high;              // high price
               double low;               // low price 
               double close;             // closing price

       };

	   struct Bar *bararray;

//Error catching function
void Error(int errorcode) 
{
 if(errorcode == 1) {
     cout << "Error in opening file...";
 }
 else cout << "OK";
}


//Function to open price data file
 int Open_Price_Data_File (char* filename)
 {
   cout << "Enter filename in the following  format c: backslash filename.csv: "; 
               cin >> filename;
               ifstream infile;
               cout << "Reading from the price data file" << endl;
               infile.open(filename); 
	if(!infile.is_open()){
	   Error (1);
		}
                  else return 0;
	infile.close();
                 return 1;
 }

			   

// Function to count number of lines in file & define the array of structures accordingly
struct Bar* Define_Array (const char* filename)
{
			   			  
	ifstream infile;			  
	infile.open(filename); 
               if(!infile.is_open())
               {
                 Error (1);
               }
	 else
                {
               string line;
               while(getline(infile, line))
               NumLines++;
               cout << "This is the total number of lines in the source file: ";
               cout << NumLines << endl; 
               Bar *bararray = NULL;
               bararray = new Bar[NumLines];
               infile.close();
               return bararray;
	         }
			 
		

}
				 

             

// String Parsing to Skip Commas
 void Parse_Output_To_File (struct Bar *dataArray, char* filename)
 {
	ofstream outfile;
                outfile.open ("c:\\Outputfile.txt");
                if (!outfile.is_open())
               {
                       cout << "Error in opening file for writing!";
               }
               else return;	 
	 
             ifstream redo;
             redo.open(filename);
             int i = 0;
 			      
               while (!redo.fail()) 			   
       {        
               int j = 0;    
               string data, token;
               getline(redo, data);
               istringstream isstream (data);
               while (getline(isstream,token,',')) 
                       {
                         outfile << token << " ";
                                 if(j == 0) {
                                       dataArray[i].date = token;
                                       j++;
                                   continue;
                       }

                               if(j == 1) {
                                       dataArray[i].open = atof( token.c_str());
                                       j++;
                                   continue;
                       }

                               if(j == 2) {
                                       dataArray[i].high = atof( token.c_str());
                                       j++;
                                       continue; 
                       }

                               if(j == 3) {
                                     dataArray[i].low = atof( token.c_str());
                                       j++;
                               continue;
                       }

                              if(j == 4) {
                                      dataArray[i].close = atof(token.c_str ());
                                      j++;
                                 continue;                     
			           }
							
							
			   }	

			        
	 i++						outfile << endl;
			   }
                redo.close()					outfile.close(); 
						
 }

// Date Verification Function

void Date_Verification (struct Bar *dataArray)
{
    cout << "This is the first date in the database: ";
    cout << dataArray[0].date << endl;
    cout << "This is the last date in the database:  ";
    cout << dataArray[NumLines - 1].date << endl;
    cout << "Enter the start date for the analysis in the mm/dd/yyyy format: ";
    string startdate;
    cin >> startdate;
    cout << "The startdate you entered is: " << startdate << endl;
							
  int i;                            
   for (i = 0; i <= NumLines -1;)
   {
								if (!strcmp(startdate.c_str(), dataArray[i].date.c_str()) == 0)	
								{
									i++;							if (i == NumLines -1)
									cout << "Incorrect start date " << endl;
								}
								else
								{
									cout << "Start date exists in the database" << endl;
									break;
								}
							}

cout << "Enter the end date for the analysis in the mm/dd/yyyy format: ";
       string enddate;
       cin >> enddate;
       cout << "The enddate you entered is: " << enddate << endl;
       for (i = 0; i <= NumLines -1;)
 {
								if (!strcmp(enddate.c_str(), dataArray[i].date.c_str()) == 0)	
									{
										i++;
										if (i == NumLines -1)
									out << "Incorrect end date" << endl;
									}
									else
									{
								cout << "End date exists in the database" << endl;
										break;
									}
		
 }

}
							



// User Prompt to Retain Command Window 
void ExitScreen ()
 {
               char ch;
               cout << "Please press Q or q to quit: ";
               cin >> ch;
               if (ch=='Q' && ch=='q') 
	{ 
	cout << "Exiting...";
			   }
               else
               cout << "Please press Q or q to quit: ";
 }


//Main Program
int main ()
{
                
	   
			   char filename [80];
			   Open_Price_Data_File (filename);
			   struct Bar* Array;
			   Array = Define_Array (filename);
			   Parse_Output_To_File (Array, filename);
			   Date_Verification (Array);
                                                     ExitScreen ();
			   return 0;
}

Can't test it since you haven't provided the input file. My best advice for now is that you need to make sure you're reading in the data in the first place. It looks like the first thing read in on line 114 is the first date, which you say is your problem. In additon to displaying it to the output file on line 116, add a line so that it displays token to the screen too. That way you see a nice list of all the tokens. See if they are correct. If not, that tells you where to go next. it's not reading the tokens correctly. If the tokens ARE being read correctly, the next step is to make sure that the tokens get into your array correctly before leaving Parse_Output_To_File. More cout statements (take them out later). You need to see exactly what's going on where to help nail down the problem. Some organized cout statements that are deleted later, along with pauses if necessary, will do wonders.

Can't test it since you haven't provided the input file. My best advice for now is that you need to make sure you're reading in the data in the first place. It looks like the first thing read in on line 114 is the first date, which you say is your problem. In additon to displaying it to the output file on line 116, add a line so that it displays token to the screen too. That way you see a nice list of all the tokens. See if they are correct. If not, that tells you where to go next. it's not reading the tokens correctly. If the tokens ARE being read correctly, the next step is to make sure that the tokens get into your array correctly before leaving Parse_Output_To_File. More cout statements (take them out later). You need to see exactly what's going on where to help nail down the problem. Some organized cout statements that are deleted later, along with pauses if necessary, will do wonders.

Hi Vernon,

Thanks for your help. I tried inserting these lines:

cout << token;
break;

right after the { outfile << token << " "; //line 117

but nothing happens when I run the program. It just goes right through to the next function, which is the date verification function... I tried inserting a cout at the beginning of the Parse_Output_To_File function and it doesn't even print that... weird. Not sure what to do next, since I'm a real newbie at troubleshooting.

Thanks much
TR.

I formatted the code to make it easier to read and added a few lines - see "Added by VD" in comments. cin.get() pauses so you have time to read. Press the "Enter" key to move on. Delete later. Add the semicolons I mention.

Make sure this displays what it is supposed to display. If it does not, everything you do afterwards relies on bad data.

// Dataprep.cpp : Defines the entry point for the console application

#include "stdafx.h"
#include <vector>
#include <fstream>
#include <iostream>
#include <string> 
#include <sstream>
#include <math.h>
#include <cstring>
using namespace std;
int NumLines;
void Error (int);
int Open_Price_Data_File (char* filename);
struct Bar* Define_Array (const char*);
void Parse_Output_To_File (struct Bar* dataArray, const char*);
void Date_Verification ();
void ExitScreen ();



//Structure Declaration and Array Initialization 
struct Bar
{
	string date;              // date
	double open;              // opening price
	double high;              // high price
	double low;               // low price 
	double close;             // closing price

};

struct Bar *bararray;

//Error catching function
void Error(int errorcode) 
{
	if(errorcode == 1) {
		cout << "Error in opening file...";
	}
	else cout << "OK";
}


//Function to open price data file
int Open_Price_Data_File (char* filename)
{
	cout << "Enter filename in the following  format c: backslash filename.csv: "; 
	cin >> filename;
	ifstream infile;
	cout << "Reading from the price data file" << endl;
	infile.open(filename); 
	if(!infile.is_open()){
		Error (1);
	}
	else return 0;
	infile.close();
	return 1;
}



// Function to count number of lines in file & define the array of structures accordingly
struct Bar* Define_Array (const char* filename)
{
	ifstream infile;			  
	infile.open(filename); 
	if(!infile.is_open())
	{
		Error (1);
	}
	else
	{
		string line;
		while(getline(infile, line))
			NumLines++;
		cout << "This is the total number of lines in the source file: ";
		cout << NumLines << endl; 
		Bar *bararray = NULL;
		bararray = new Bar[NumLines];
		infile.close();
		return bararray;
	}
}




// String Parsing to Skip Commas
void Parse_Output_To_File (struct Bar *dataArray, char* filename)
{
	ofstream outfile;
	outfile.open ("c:\\Outputfile.txt");
	if (!outfile.is_open())
	{
		cout << "Error in opening file for writing!";
	}
	else return;	 

	ifstream redo;
	redo.open(filename);
	int i = 0;

	while (!redo.fail()) 			   
	{        
		int j = 0;    
		string data, token;
		getline(redo, data);
		istringstream isstream (data);
		while (getline(isstream,token,',')) 
		{
			outfile << token << " ";
			cout << "i = " << i << ", j = " << j << ", token = " << token << endl;  // added by VD
			cin.get ();  // added by VD
			if(j == 0) 
			{
				dataArray[i].date = token;
				j++;
				continue;
			}

			if(j == 1) 
			{
				dataArray[i].open = atof( token.c_str());
				j++;
				continue;
			}

			if(j == 2) {
				dataArray[i].high = atof( token.c_str());
				j++;
				continue; 
			}

			if(j == 3) {
				dataArray[i].low = atof( token.c_str());
				j++;
				continue;
			}

			if(j == 4) {
				dataArray[i].close = atof(token.c_str ());
				j++;
				continue;                     
			}

			cout << "j = " << j << ".  None of the if statements executed." << endl; // added by VD.
			cin.get (); // added by VD.
		}	


		i++  // add semicolon - VD
		outfile << endl;
	}
	redo.close()  // add semicolon - VD
	outfile.close(); 
}

// Date Verification Function

void Date_Verification (struct Bar *dataArray)
{
	cout << "This is the first date in the database: ";
	cout << dataArray[0].date << endl;
	cout << "This is the last date in the database:  ";
	cout << dataArray[NumLines - 1].date << endl;
	cout << "Enter the start date for the analysis in the mm/dd/yyyy format: ";
	string startdate;
	cin >> startdate;
	cout << "The startdate you entered is: " << startdate << endl;

	int i;                            
	for (i = 0; i <= NumLines -1;)
	{
		if (!strcmp(startdate.c_str(), dataArray[i].date.c_str()) == 0)	
		{
			i++;
			if (i == NumLines -1)
				cout << "Incorrect start date " << endl;
		}
		else
		{
			cout << "Start date exists in the database" << endl;
			break;
		}
	}

	cout << "Enter the end date for the analysis in the mm/dd/yyyy format: ";
	string enddate;
	cin >> enddate;
	cout << "The enddate you entered is: " << enddate << endl;
	for (i = 0; i <= NumLines -1;)
	{
		if (!strcmp(enddate.c_str(), dataArray[i].date.c_str()) == 0)	
		{
			i++;
			if (i == NumLines -1)
				out << "Incorrect end date" << endl;
		}
		else
		{
			cout << "End date exists in the database" << endl;
			break;
		}
	}
}




// User Prompt to Retain Command Window 
void ExitScreen ()
{
	char ch;
	cout << "Please press Q or q to quit: ";
	cin >> ch;
	if (ch=='Q' && ch=='q') 
	{ 
		cout << "Exiting...";
	}
	else
		cout << "Please press Q or q to quit: ";
}


//Main Program
int main ()
{
	char filename [80];
	Open_Price_Data_File (filename);
	struct Bar* Array;
	Array = Define_Array (filename);
	Parse_Output_To_File (Array, filename);
	Date_Verification (Array);
	ExitScreen ();
	return 0;
}

Hi Vernon,

I was careful to add the code you suggested. I also made sure the semi colons were there (they were in the original code). Very strange, but I get exactly the same result, i.e., prints:

Reading from the price data file
This is the total number of lines in the source file: 18066
This is the first date in the database:
This is the last date in the database:
Enter the start date for the analysis in the mm/dd/yyyy format:

My inferences so far:
#1 If it's still not printing the first date then it means that the array of structures did not populate.

#2 If it didn't print the j cout you suggested it means that it's not even reading from the file? i.e., the getline (redo,data) isn't doing its job?

#3 I know that the output file is opened (see it on my C drive) but nothing is sent to it because the file is empty.

#4 I also know that the problem is not the source file because I opened it up and there whole 18066 lines are there.

So if the data source is not the problem it has to be the code?

Thanks much
TR

If you don't get any of the lines that I added as cout statements, that means that they aren't being executed even once, so it's breaking somewhere, and very early.

Whether the code is the problem or the input file is the problem, I can't say since I haven't seen the input file. Did you upload it? If so, I don't see it. I don't need an 18,000 line input file. A much shorter one will suffice, but give at least a few lines. That would be the fastest way. That way we can run it, see if the file matches the program, etc.

Actually, regardless of the file, this code (starting at line 92) seems seriously off and is very likely the culprit. In fact, since your output doesn't show any error messages, it certainly IS the culprit.

ofstream outfile;
	outfile.open ("c:\\Outputfile.txt");
	if (!outfile.is_open())
	{
		cout << "Error in opening file for writing!";
	}
	else return;

You are returning when the file opens SUCCESSFULLY (i.e. when you DO NOT get an error. Assuming everything works the way it is supposed to, you're returning at line 98, before you even open the input file. I can't imagine that you intend to do that. I imagine that you instead want this:

ofstream outfile;
	outfile.open ("c:\\Outputfile.txt");
	if (!outfile.is_open())
	{
		cout << "Error in opening file for writing!";
                return;
	}

Get rid of the "else" statement altogether. Relocate the return statement. You want to short-circuit the function if you get an error, I would imagine, not if everything is working fine?

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.