• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 277
  • Last Modified:

Reading file with get().

Hi all,

I have a .txt-file with a random number (eg zipcodes, size is varying though) followed by a string (eg city name) on each line.
My intention is to read the file line per line and place the number in an int and the 'city name' in a string, to use both parameters in a constructor later on.
I'm not sure if I'm doing something wrong with the string pointer declaration or with the get()function..I was trying to have the number delimited by the space inbetween number and name on the file. I'm new at C++, programming altogether. Would anyone have any suggestion?


#include <iostream.h>
#include <fstream.h>

void main()
{
     ifstream in;
     ofstream out;

     char ch;
     char* zipcode;
     char* cityname;


     in.open("postcody.txt");
        while (!in.eof()) {
//          in.get(ch);
          in.get(zipcode, ' ');
          if (!in.eof())
          {
//               cout << ch;  
               out << cityname;
               in.close();

          }
     }

     in.close();
     cout << endl << "done" << endl;
}
0
Marty21
Asked:
Marty21
  • 6
  • 2
  • 2
  • +4
1 Solution
 
Marty21Author Commented:
Actually I forgot to mention that the reason I wrote this is also because when I run this program as is above, executing it let's the console crash for some reason...

I'll convert the zipcode-string later on in an int. Is this a preferred way to do it?


0
 
IvaandrCommented:
#include <iostream.h>
#include <fstream.h>

void main()
{
    ifstream in;
    ofstream out;

    char ch;
    char zipcode[6];  //NOTE, that length of zipcode must be equivalent vith length from file
    char cityname[255];  //try 255, if length of cityname not more, than 255


    in.open("postcody.txt");
       while (!in.eof()) {
         in.get(zipcode,6);
         in.get(cityname,255);
         cout<<"zip:"<<zipcode<<";city: "<<cityname<<endl;
        }
    in.close();
    cout << endl << "done" << endl;
}
0
 
madfaceCommented:
insted of char* for zipcode and cityname try
char zipcode[20];

your pointers where not initizied so they are pointing in odd spots. Also i beleive get() will not allocate memory for you so you must use an array.
0
Concerto's Cloud Advisory Services

Want to avoid the missteps to gaining all the benefits of the cloud? Learn more about the different assessment options from our Cloud Advisory team.

 
Marty21Author Commented:
Actually I forgot to mention that the reason I wrote this is also because when I run this program as is above, executing it let's the console crash for some reason...

I'll convert the zipcode-string later on in an int. Is this a preferred way to do it?


0
 
oferhCommented:
why dont you do:

in.open("postcody.txt");
      while (!in.eof()) {
         in >>zipcode >>cityname;
}
       
0
 
Marty21Author Commented:
(sorry for the earlier repeated comment, refreshing this page is not allowed it seems..)

So, using get(), I'm not able to let the program decide at runtime how many chars need to be read..? (in case of different zipcode sizes (US <-> European). That's why I was trying to figure out a way through pointers. I have tried to add
char* zipcode = NULL;

but that still gave the execute-crash..
0
 
Marty21Author Commented:
I tried that oferh,
it still crashes on me..
Doing that does that mean it automatically skips all whitespaces?

0
 
SalteCommented:
One minor point.

Not sure if it is smart to specify zip code as number. For US and possibly for most countries there are numeric codes for this kind of thing, but they often have letters or something around them. For example in Norway we use a 4 digit number as zip code but if sending from abroad we sometimes prefix that 4 digit number with "N-" indicating 'Norway' so a zipcode of 1234 would be N-1234. Such a zip code would crash if you require the zipcode to be a pure number.

I think the safest bet is to just treat the zipcode like a string just like the city name. It just often happen to be a number but that is irrelevant. If you want an integer for fast lookup, use a hash function from the zipcode string and use the integer value from that hashfunction as your integer value.

Alf
0
 
Marty21Author Commented:
It's more that I'm trying to challenge myself with goals I set forward for myself.
The idea was to arrange citynames using the postalcodes int value (in ascending order), eventually using balanced trees..I have a long way to go, but it kinda bothers me that I'm losing time trying to figure out why I get this error when I execute.

"reading.exe has encountered a problem and needs to close. We are sorry for the inconvenience. (with of course no further explanation really except some dump code)"

I was using postal codes coz I had a file already written in that format. But in the end I didn't want to restrict myself to just the 6 numbers of the USA...I wanted eventually to use a file that could have numbers from 1-1 million or so. That's why I was hoping using pointers would've helped me out. But according to this error message it won't let me.
You're right I was going to use the zipcode as string and then convert it to int. As for hashfunction, I have read something about hashtables but I haven't been quite into that. If I can't find no answer on the net here I guess I'll have to change my goals, like you said, but in my eyes it would be a shame not to learn why it didn't work :).
0
 
jadams117Commented:
I think the code below solves your problem. It's better to use the std::string class to hold strings if you don't know their length beforehand as it will be allocated dynamically as needed. Your crash was caused by the uninitialised char* pointers..

#include <fstream>
#include <iostream>
#include <string>
#include <conio.h>

int main()
{
     std::ifstream inFile("temp.txt");

     std::string zip;
     std::string city;

     while (!inFile.eof())
     {
          inFile >> zip >> city;
          std::cout << zip << ' ' << city << '\n';
     }

     while (!kbhit());
     return 0;
}
0
 
DarthNemesisCommented:
Do you have any objections to working with a string object? Character arrays are more efficient when your data is strictly organized, but it's a pain to try to allocate them correctly when you don't know how long they have to be.

BTW, your program was crashing becase you declared the variables as pointers but didn't allocate any memory for them, i.e. char* zipcode = new char[5].

Anyway, here's an example using strings that works fine:

#include <iostream.h>
#include <fstream.h>
#include <string.h>
using namespace std;

void main()
{
        ifstream in("postcody.txt");
        string zipcode, cityname;
        while (!in.eof()) {
                in >> zipcode >> cityname;
                // add storage operations here
                cout << zipcode << " " << cityname << endl;
        }

        in.close();
        cout << endl << "done" << endl;
}

And yes, the extraction operator >> ignores whitespace.
0
 
jadams117Commented:
By the way:

The std:: parts indicate that the names 'ifstream', 'string' and 'cout' lie within the std namespace. This namespace is a convention used within the standard c++ libraries to prevent name-clashes in case you have any other objects with those same names

The line 'while (!kbhit());' is just a way of waiting for a keyboard event so that the DOS window doesn't close before you've read what's on the screen
0
 
Marty21Author Commented:
Thanks for your replies, I'm glad there are people like you willing to help people like me..:)
I was still wondering..

suppose the cityname has whitespaces still in its name (before the end of the line, but that I still need, like eg "Los Angeles"), how do I avoid the ifstream in to consider Angeles as a zipcode?
I've been trying things like (among others)
in.get(cityname,255,'\n');
but that didn't work..any ideas still?


(Also, I feel like both DarthNemesis and jadams117 should get points because both of you really helped me, but I'm afraid I can only give one of you points right (is there any way around this?)..I'll just use the time-factor then..(sorry DarthNemesis..can I reward you later on?))
0
 
DarthNemesisCommented:
All you should have to do is change one of the >> operators to getline:

#include <iostream>
#include <fstream>
#include <string>
using namespace std;

void main()
{
       ifstream in("postcody.txt");
       string zipcode, cityname;
       while (!in.eof()) {
               in >> zipcode;
            getline(in, cityname);
               // add storage operations here
               cout << zipcode << " " << cityname << endl;
       }

       in.close();
       cout << endl << "done" << endl;
}

As for giving me points too, thanks, you can just start a new problem with a title like "Points for DarthNemesis" and I'll respond to it.
0

Featured Post

VIDEO: THE CONCERTO CLOUD FOR HEALTHCARE

Modern healthcare requires a modern cloud. View this brief video to understand how the Concerto Cloud for Healthcare can help your organization.

  • 6
  • 2
  • 2
  • +4
Tackle projects and never again get stuck behind a technical roadblock.
Join Now