1

I'm trying to read in a csv file and then use what is read in to create objects. These objects will form a linked list.

When I open the csv file in notepad it looks something like this:

Name,Location Bob Smith,Los Angeles Joe Smow,New York Generic Name,Phoenix

I want to skip over the first row (Name,Location) and read in the rest.

Right now my code looks like this:

ifstream File("File.csv");  

string name, location, skipline;

if(File.is_open())
{
    //Better way to skip the first line?
    getline(File, skipline, ',');
    getline(File, skipline);


    while (File.good())
    {
        getline(File, name, ',');


        getline(File, location);


        //Create new PersonNode (May not need the null pointers for constructor)
        PersonNode *node = new PersonNode(name, location, nullptr, nullptr);


        //Testing
        cout << node->getName() << " --- " << node->getLocation() << endl;

        //Add HubNode to linked list of Hubs (global variable hubHead)
        node->setNext(hubHead);
        hubHead = node;
    }
}
else
{
    cout << "Error Message!" << endl;
}

This seems to read in the file OK for the most part, but is there a better way to skip the first row? Also, when the file is printed out the second row of the last column is duplicated so it looks like this:

Input:

Name,Location Bob Smith,Los Angeles Joe Smow,New York Generic Name,Phoenix

The output is:

Bob Smith --- Los Angeles Joe Smow --- New York Generic Name --- Phoenix --- Phoenix

If it is relevant, the constructor for the objects looks like this (the OtherNode is going to be used because another linked list will involved, but I'm not worrying about that yet).

PersonNode::PersonNode(string name, string location, Node *next, OtherNode *head) { PersonNode::name = name; PersonNode::location = location; PersonNode::next = next; PersonNode::OtherNode = OtherNode; }

Thanks for any help, it is greatly appreciated.

SuperCow
  • 1,523
  • 7
  • 20
  • 32
  • I don't understand why your cout statement doesn't use `std::endl` You seem to be stuck on some C conventions. Also, it doesn't look like your linked list needs to know where the next is at construction time, or the head for that matter, so why does the constructor need those to be passed in? You can just assume that next will be `nullptr` if it always will be anyway at construction time. – ciphermagi Mar 21 '14 at 21:49
  • Yeah I am coming from just learning a little bit about C. I have "using namespace std;" I didn't know I could have more than one thing like that. So, if I have "std::endl" do I not need to use the escape character \n or I guess I'm not really sure what that does. As far as the constructor, I see what you are saying (I think). So following the object being created then I'd have another line of code that would actually add it to the linked list? – SuperCow Mar 21 '14 at 22:10
  • I understand from your code that you're using the namespace `std`, but that doesn't address the purpose of my comment, which is: Why are you using C code && why are you complicating the object contruction? – ciphermagi Mar 21 '14 at 22:11
  • Exactly which part is the C code? And how should it be changed? (Sorry, pretty new at this). And as far as the object construction I see what you are saying (I think). So following the object being created then I'd have another line of code that would actually add it to the linked list? – SuperCow Mar 21 '14 at 22:16
  • `"\n"` is a C newline character. `std::endl` or `endl` (if you're using namespace std) is the endline keyword for C++. And `std::cout` can handle string literals just fine. You don't have to convert them. – ciphermagi Mar 21 '14 at 22:18
  • Thanks for the suggestion, always eager to learn. I updated the code to reflect the changes and also set up a way to add to the linked list. (global variables are OK to use in the current scope of this project). – SuperCow Mar 21 '14 at 23:14
  • possible duplicate of [CSV parser in C++](http://stackoverflow.com/questions/1120140/csv-parser-in-c) – gbjbaanb Mar 22 '14 at 13:56

1 Answers1

1

I don't think you need getline(File, skipline, ','); to skip the first line. Because getline(File, skipline); will already skip the first line

From (documentation):

(1) istream& getline (istream& is, string& str, char delim);
(2) istream& getline (istream& is, string& str);

Extracts characters from is and stores them into str until the delimitation character delim is found (or the newline character, '\n', for (2)).

You'll need getline(File, skipline, ','); though to get values inside your loop

Jay-Ar Polidario
  • 6,463
  • 14
  • 28
  • Good catch, thank you for that. I only needed getline(File skipline);. Any idea why I still get the extra --- Phoenix at the end? – SuperCow Mar 22 '14 at 02:28
  • hmm I'm not sure but my guess is that somehow there's an extra `newline` at the very end of the csv file, so the `while(File.good())` still loops. Can you try this `getline(File, location, '\n');` instead of `getline(File, location)`? If this still couts an extra Phoenix, my last guess is that since the last value of location is Phoenix, and there's this extra 'newline' at the very end of the csv file, the while loop still continued and then somehow displayed the last value of `location` which is Phoenix, while the `name` is not outputted for unknown reasons – Jay-Ar Polidario Mar 22 '14 at 16:05