Thread: string input problem

  1. #1
    Registered User
    Join Date
    Jun 2003
    Posts
    81

    string input problem

    I am trying to create an inventory-esque program. I want to be able to enter in some data about a product and then save it into another struct and then enter another if so desired. The problem is i enter in one item and all of it's properties and then when it loops around to enter another one, it skips the forst entry. I think it has to do with my string instruction.

    Here is the code:
    Code:
    #include <iostream>
    #include <string>
    #include <fstream>
    #include <cstdlib>
    #include <conio.h>
    #include <iomanip>
    
    using namespace std;
    
    	struct co {
    		string name;      //Product Name
    		string model;     //Model Number
    		string descrip;   //Description
    		double Rprice;    //Retail price
    		double priceP;    //Price Paid
    	};
    
    int main()
    {
    	//After data is entered, save it into another struct to be searched later.
    	//Create counter
        int proceed=1;
    	string decision;
    
    	co inven;     //Declare struct for inventory
    	while(proceed)
    	{
    		cout<<"Enter the Product name: ";  //Product Name
    		getline ( cin, inven.name );
    		cout<<"Enter the Model number: ";  //Model Number
    		getline(cin,inven.model); 
    		cout<<"Enter Description of Item: ";  //Description
    		getline(cin,inven.descrip); 
    		cout<<"Retail Price Paid: ";       //Retail Price
    		cin>>inven.Rprice;
    		cout<<"Actual Price Paid: ";       //Price Paid
    		cin>>inven.priceP;
    		cout<<"Would you like to add another item? (Yes/No) ";
    		cin >> decision;
    		if (decision!="yes")
    			proceed=0;
    		else
    			proceed=1;
    	}
    		//Display
    	cout <<"\n-----------------------------------------------\n" << endl;
    	cout << "Product Name: " << inven.name << endl;
    	cout << "Model Number: " << inven.model << endl;
    	cout << "Product Description: " << inven.descrip << endl;
    	cout << "Retail Price: $" << inven.Rprice << endl;
    	cout << "Actual Price: $" << inven.priceP << endl;
    return 0;
    }
    Output Problem after first item & description was entered.
    Code:
    Enter the Product name: Enter the Model number:
    Any help would be much appreciated.
    Gracias.

  2. #2
    Code Goddess Prelude's Avatar
    Join Date
    Sep 2001
    Posts
    9,897
    This is a common problem. In fact, everyone re-discovers it when they start working with C or C++. The problem is that formatted input functions don't mix well with unformatted input functions because the formatted input functions (ie. >> and scanf) treat newlines differently than common unformatted input functions (ie. getline and fgets). A quick fix is to just discard any leftover characters in the stream:
    Code:
    #include <iostream>
    #include <string>
    #include <fstream>
    #include <cstdlib>
    #include <conio.h>
    #include <iomanip>
    #include <limits>
    
    using namespace std;
    
    struct co {
      string name;      //Product Name
      string model;     //Model Number
      string descrip;   //Description
      double Rprice;    //Retail price
      double priceP;    //Price Paid
    };
    
    int main()
    {
      //After data is entered, save it into another struct to be searched later.
      //Create counter
      int proceed=1;
      string decision;
    
      co inven;     //Declare struct for inventory
      while(proceed)
      {
        cout<<"Enter the Product name: ";  //Product Name
        getline ( cin, inven.name );
        cout<<"Enter the Model number: ";  //Model Number
        getline(cin,inven.model); 
        cout<<"Enter Description of Item: ";  //Description
        getline(cin,inven.descrip); 
        cout<<"Retail Price Paid: ";       //Retail Price
        cin>>inven.Rprice;
        cout<<"Actual Price Paid: ";       //Price Paid
        cin>>inven.priceP;
        cout<<"Would you like to add another item? (Yes/No) ";
        cin >> decision;
        if (decision!="yes")
          proceed=0;
        else
          proceed=1;
        cin.ignore ( numeric_limits<streamsize>::max(), '\n' );
      }
      //Display
      cout <<"\n-----------------------------------------------\n" << endl;
      cout << "Product Name: " << inven.name << endl;
      cout << "Model Number: " << inven.model << endl;
      cout << "Product Description: " << inven.descrip << endl;
      cout << "Retail Price: $" << inven.Rprice << endl;
      cout << "Actual Price: $" << inven.priceP << endl;
      return 0;
    }
    My best code is written with the delete key.

  3. #3
    Registered User
    Join Date
    Jun 2003
    Posts
    81
    Thanks, that helped a lot. I may have some more questions concerning structs. Would it be easier to use classes? I haven't gone over this stuff in about a year. Just brushing up.

  4. #4
    Code Goddess Prelude's Avatar
    Join Date
    Sep 2001
    Posts
    9,897
    >Would it be easier to use classes?
    It depends on the use. If you're using something very simple like a point then a struct is easier because you don't have to worry about access specifiers. public is the default:
    Code:
    struct point {
      int x, y;
    };
    If you used a class then you would have to explicitly say that the data is public:
    Code:
    class point {
    public:
      int x, y;
    };
    On the other extreme, if you're creating an object with private data then a class would more clearly show your intentions. In the end, there's no difference at all between classes and structs aside from the name and the default access level.
    My best code is written with the delete key.

  5. #5
    Registered User
    Join Date
    Jun 2003
    Posts
    81
    Is there anyway to create a counter to be incrimented and added to a struct name like:

    Code:
    int elem=0;
    
    elem++;
    //create struct to hold copied data
    struct DataCopy;
    //add incrimented variable to struct name
    DataCopy+elem;
    This might be an easy thing to do and maybe I'm looking somthing over, but any help will be great.

  6. #6
    carry on JaWiB's Avatar
    Join Date
    Feb 2003
    Location
    Seattle, WA
    Posts
    1,972
    If I understand your question correctly, it wouldn't be too difficult. Check the faq on how to convert an int to a string and then it should be easy since you are using the std::string object.
    "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

  7. #7
    Code Goddess Prelude's Avatar
    Join Date
    Sep 2001
    Posts
    9,897
    >Is there anyway to create a counter to be incrimented and added to a struct name
    Can you rephrase your question? I don't understand what you're trying to do, so suggesting a solution would likely be counter-productive.
    My best code is written with the delete key.

  8. #8
    Registered User
    Join Date
    Aug 2004
    Location
    San Diego, CA
    Posts
    313
    Prelude: What the question means is, "Can I create a struct name dynamically based on an interger counter."

    Unfortunately, I don't know what the answer to that would be, but I suspect you can't. Last I knew, variable names had to be declared at compile-time.



    Edit: Something like -

    Struct0
    Struct1
    Struct2
    Struct3
    ...
    StructN
    Last edited by Lithorien; 06-26-2005 at 08:19 PM.

  9. #9
    Registered User
    Join Date
    Jun 2003
    Posts
    81
    Lithorien re-phrased my question perfectly. However, I will try JaWiB's idea.. I just took a class in Python and it seemed to be more user friendly than C++ is.. I guess I'm just spoiled. I'll let you know the outcome. If you have anymore ideas, please post away.

    Thanks

  10. #10
    Code Goddess Prelude's Avatar
    Join Date
    Sep 2001
    Posts
    9,897
    >Can I create a struct name dynamically based on an interger counter.
    That's what I though, but it never hurts to ask for clarification. The answer is no; and yes, but it's not advisable; and yes, but it's not what you're thinking.

    Being less cryptic, no, you can't do it normally. However, you can fake it by using the preprocessor, but the preprocessor causes too many problems for that solution to be a good one. You can also simulate similar behavior by using a map keyed on the integer. That's usually the best solution, but people coming from high level scripting languages find it overly verbose:
    Code:
    #include <iostream>
    #include <map>
    #include <string>
    
    using namespace std;
    
    struct data {
      string s;
      data() {}
      data ( const string& init ): s ( init ) {}
    };
    
    int main()
    {
      map<int, data> data_map;
      int counter = 0;
    
      data_map[++counter] = data ( "test" );
      data_map[++counter] = data ( "another test" );
    
      map<int, data>::iterator it = data_map.begin();
    
      while ( it != data_map.end() ) {
        cout<<"data"<< it->first <<": "<< it->second.s <<'\n';
        ++it;
      }
    }
    My best code is written with the delete key.

  11. #11
    Registered User
    Join Date
    Jun 2003
    Posts
    81
    Instead of doing anything too complicated, it came down to something as simple as using the string conversion in the FAQ and this code:
    Code:
      int number=5;
      string test="data";
      string final;
      cout << "int: " << number << " string: " << result << endl;
      final=test+result;
      cout << final << endl;
    Thanks for all the help.
    If (i have anymore questions)
    {
    I'll post.
    }

  12. #12
    Registered User
    Join Date
    Jun 2003
    Posts
    81
    Well, I guess I got so caught up in trying to add two strings together I forgot why I was trying to do it in the first place. I tried creating a new struct from the combined string and that obviously did not work. I guess I will try another method of cataloging.

  13. #13
    Code Goddess Prelude's Avatar
    Join Date
    Sep 2001
    Posts
    9,897
    >I tried creating a new struct from the combined string and that obviously did not work.
    Right, you can't declare an object using the value of a string as the type. But I figured I would let you give it a shot first. There's no knowledge like knowledge born of experience.

    >I guess I will try another method of cataloging.
    As I said before, std::map is your easiest option. Everything else would involve you basically implementing your own associative array or using a non-portable library.
    My best code is written with the delete key.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. char Handling, probably typical newbie stuff
    By Neolyth in forum C Programming
    Replies: 16
    Last Post: 06-21-2009, 04:05 AM
  2. Checking array for string
    By Ayreon in forum C Programming
    Replies: 87
    Last Post: 03-09-2009, 03:25 PM
  3. can someone help me with these errors please code included
    By geekrockergal in forum C Programming
    Replies: 7
    Last Post: 02-10-2009, 02:20 PM
  4. string problem
    By INeedSleep in forum C++ Programming
    Replies: 24
    Last Post: 11-08-2007, 11:52 PM
  5. ........ed off at functions
    By Klinerr1 in forum C++ Programming
    Replies: 8
    Last Post: 07-29-2002, 09:37 PM