Thread: Carrying ints a chars over to other functions.

  1. #16
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    You might be looking to use strlen() instead. chFunc1 is a pointer, not an object of a class type that has a size() member function.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  2. #17
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    There are two main ways to handle a string. One is to use character arrays, the other is to use the C++ string class. In C++ using the C++ string class is generally the better option, but sometimes classes/books/tutorials are old and unmodernized or just disagree and use character arrays instead.

    So if you can, then I'd suggest using the C++ string class. That means using string instead of char* or char[]. The C++ string class has a function called size(), and if chFunc1 was a string then your call to size() would work.

    However, if you are being taught character arrays, then I guess you should use those for now and strlen is what you need for the size. Just remember to learn C++ strings on your own later if you want to continue with C++.

  3. #18
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    can i still refer to an individual character if i use the string class?

  4. #19
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Yes.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  5. #20
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    ok, string class seems to help, but I have now lead myself to another problem, of which I just can't seem to figure out. I know it's a little unorthodox, but, if you don't mind, I'm going to post my entire source code here (it's not very long) to see what you guys make of it. This particular one is for a friend of mine who wants to randomly capitalize email addresses.
    Code:
    #include <iostream>
    #include <cstdlib>
    #include <time.h>
    #include <cctype>
    #include <windows.h>
    #include <string.h>
    #include <fstream>
    #include <sstream>
    using namespace std;
    /*
    These constants define our upper
    and our lower bounds. The random numbers
    will always be between 1 and 12, inclusive.
    */
    const int LOW = 1;
    const int HIGH = 12;
    
    string getAddy() // Get the email address from the user...pretty self-explanatory...
    {
           cout << "Enter address below: ";
           string addy;
           getline(cin,addy);
           cout << "\nDid you enter \"" << addy << "\"? [y|n]: ";
           char yn;
           cin >> yn;
           switch ( yn ) {
                  case 'y':
                       break;
                  case 'n':
                       cout << "\nPlease try again." << endl;
                       getAddy();
                  default:
                          cerr << "\nInvalid selection. Please try again." << endl;
                          getAddy();
                  }
           return addy;
    }
    
    string randomize()
    {
         string addy = getAddy(); // Puts the value of getAddy into a string
         int len = addy.size(); // Get the length of the string
         string randAddy;                            //
         string usedAddies;                          // 
         ifstream used_addies ("addies.txt");        // Makes sure that no two addies
         while (! used_addies.eof()) {               // generated are the same.
               getline(used_addies, usedAddies); }   //
         used_addies.close();                        //
         stringstream str_randAddy;                  //
         for (int i=1; i <= len; i++) {
             if (rand() < HIGH * 0.15) {
                        randAddy[i] = toupper(addy[i]); // Capitilize some random characters
                        }
             }
         str_randAddy << randAddy;
         if (usedAddies.find(str_randAddy.str(), 0) != std::string::npos) { // If it's already been made, start over
                                                 randomize(); }
         return randAddy;
    }
    
    void saveAddy() // Save the randomized addy to addies.txt ...again pretty self-explanatory...
    {
         string addy = randomize();
         ofstream addies ("addies.txt", ios::app);
         if (addies.is_open()) {
            addies << addy << ", ";
            }
            /*
            If there was a problem
            opening the file, terminate
            the program.
            */
         else {
              cerr << "Error: Could not open log file. 10 seconds 'till quit.";
              for (int i=10; i=0; i--) {
                  cout << i;
                  Sleep(1000);
                  }
              abort();
              }
         return;
    }
    
    int main()
    {
        getAddy();
        cout << "How many addies are req'd? : "; // tells the program how many addies to generate
        int reqd;
        cin >> reqd;
        for (int i=0; i <= reqd; i++) {
            randomize();
            saveAddy(); }
        cout << "Finished generating addies!!" << endl;
        system("PAUSE");
        return 0;
    }
    If you don't feel like compiling it, this is what the screen looks like...
    http://i12.tinypic.com/2vvnhvb.jpg
    Last edited by jmajeremy; 04-01-2007 at 02:22 PM.

  6. #21
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    You are mixing cin >> with getline. That leads to problems because when the user types in something like the 5 to answer the How many addies are req'd question, they type 5<enter>. The <enter> leaves a newline character in the input stream, but cin >> does not read that in, it leaves it there for later. When you call getline to get the address, it looks for the next newline character and it finds the one leftover from the previous <enter>. That's why the email address is empty.

    The solution is to add cin.ignore() after any call to cin >> to ensure that the newline character is ignored. You shouldn't add the ignore() after calls to getline() because unlike operator>>, getline() automatically reads and ignores the newline it finds at the end.

  7. #22
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    if i put getline(), cin.ignore(), or if i jst change it to:
    Code:
    for (int i=0; i <= 10; i++) {
            randomize();
            saveAddy(); }
    , I get the same result.

  8. #23
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    its still doing the same thing

  9. #24
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    You put cin.ignore() immediately after all calls to cin >> and it didn't change anything? Can you post your latest code with that change?

  10. #25
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    Should it be wriiten as...
    Code:
    cin >> var;
    cin.ignore();
    
    // or
    
    cin.irgnore() >> var;
    ?

  11. #26
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Use the former.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  12. #27
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    Quote Originally Posted by Daved View Post
    You put cin.ignore() immediately after all calls to cin >> and it didn't change anything? Can you post your latest code with that change?
    Here's the updated code...
    Code:
    #include <iostream>
    #include <cstdlib>
    #include <time.h>
    #include <cctype>
    #include <windows.h>
    #include <string.h>
    #include <fstream>
    #include <sstream>
    using namespace std;
    /*
    These constants define our upper
    and our lower bounds. The random numbers
    will always be between 1 and 12, inclusive.
    */
    const int LOW = 1;
    const int HIGH = 12;
    
    string getAddy() // Get the email address from the user...pretty self-explanatory...
    {
           cout << "Enter address below: ";
           string addy;
           getline(cin,addy);
           cout << "\nDid you enter \"" << addy << "\"? [y|n]: ";
           char yn;
           cin >> yn;
           cin.ignore();
           switch ( yn ) {
                  case 'y':
                       break;
                  case 'n':
                       cout << "\nPlease try again." << endl;
                       getAddy();
                  default:
                          cerr << "\nInvalid selection. Please try again." << endl;
                          getAddy();
                  }
           return addy;
    }
    
    string randomize()
    {
         string addy = getAddy(); // Puts the value of getAddy into a string
         int len = addy.size(); // Get the length of the string
         string randAddy;                            //
         string usedAddies;                          // 
         ifstream used_addies ("addies.txt");        // Makes sure that no two addies
         while (! used_addies.eof()) {               // generated are the same.
               getline(used_addies, usedAddies); }   //
         used_addies.close();                        //
         stringstream str_randAddy;                  //
         for (int i=1; i <= len; i++) {
             if (rand() < HIGH * 0.15) {
                        randAddy[i] = toupper(addy[i]); // Capitilize some random characters
                        }
             }
         str_randAddy << randAddy;
         if (usedAddies.find(str_randAddy.str(), 0) != std::string::npos) { // If it's already been made, start over
                                                 randomize(); }
         return randAddy;
    }
    
    void saveAddy() // Save the randomized addy to addies.txt ...again pretty self-explanatory...
    {
         string addy = randomize();
         ofstream addies ("addies.txt", ios::app);
         if (addies.is_open()) {
            addies << addy << ", ";
            }
            /*
            If there was a problem
            opening the file, terminate
            the program.
            */
         else {
              cerr << "Error: Could not open log file. 10 seconds 'till quit.";
              for (int i=10; i=0; i--) {
                  cout << i;
                  Sleep(1000);
                  }
              abort();
              }
         return;
    }
    
    int main()
    {
        getAddy();
        cout << "How many addies are req'd? : "; // tells the program how many addies to generate
        int reqd;
        cin >> reqd;
        cin.ignore();
        for (int i=0; i <= reqd; i++) {
            randomize();
            saveAddy(); }
        cout << "Finished generating addies!!" << endl;
        system("PAUSE");
        return 0;
    }
    ...although I don't think that was the problem, because the first time I enter the addy it works, but then it tries to (unsuccessfully) do getAddy() again, even though it's written to call randomize() and then saveAddy().

  13. #28
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Code:
    string getAddy() // Get the email address from the user...pretty self-explanatory...
    {
           cout << "Enter address below: ";
           string addy;
           getline(cin,addy);
           cout << "\nDid you enter \"" << addy << "\"? [y|n]: ";
           char yn;
           cin >> yn;
           cin.ignore();
           switch ( yn ) {
                  case 'y':
                       break;
                  case 'n':
                       cout << "\nPlease try again." << endl;
                       getAddy();
                  default:
                          cerr << "\nInvalid selection. Please try again." << endl;
                          getAddy();
                  }
           return addy;
    }
    When you recur and call getAddy(), you ignore its return value. I suggest you use
    Code:
    return getAddy();
    in the places I have highlighted.

    Code:
    void saveAddy() // Save the randomized addy to addies.txt ...again pretty self-explanatory...
    {
         string addy = randomize();
         ofstream addies ("addies.txt", ios::app);
         if (addies.is_open()) {
            addies << addy << ", ";
            }
            /*
            If there was a problem
            opening the file, terminate
            the program.
            */
         else {
              cerr << "Error: Could not open log file. 10 seconds 'till quit.";
              for (int i=10; i=0; i--) {
                  cout << i;
                  Sleep(1000);
                  }
              abort();
              }
         return;
    }
    First of all, you never close the file addies. If you try to open this file at a later point in the program (perhaps with this same function), it probably won't work, because it's still open. Make sure you call
    Code:
    addies.close();
    if it was opened successfully.

    Secondly, the loop highlighted in red will never execute.
    Code:
    for (int i=10; i=0; i--) {
    i=0 is always false. I'm guessing you meant i>0.

    Thirdly, the blue-highlighted line (assuming you fix the loop) will generate output like
    Code:
    10987654321
    I suggest printing a newline after it (or to be really fancy and non-portable, '\r' ). (Also a newline or at least a space after the preceding cerr message.)

    Fourth, that return statement is optional.

    Code:
         string randAddy;                            //
         string usedAddies;                          // 
         ifstream used_addies ("addies.txt");        // Makes sure that no two addies
         while (! used_addies.eof()) {               // generated are the same.
               getline(used_addies, usedAddies); }   //
         used_addies.close();                        //
         stringstream str_randAddy;                  //
    At the end of that while loop, used_addies will contain the last line in the file. I think you probably want an array or all of the lines in the file appended to each other, unless you only want to consider the last addie.

    Code:
         stringstream str_randAddy;                  //
         for (int i=1; i <= len; i++) {
             if (rand() < HIGH * 0.15) {
                        randAddy[i] = toupper(addy[i]); // Capitilize some random characters
                        }
             }
    I think you're accessing beyond the end of the array there.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

  14. #29
    Registered User
    Join Date
    Nov 2006
    Posts
    31
    ok, here's the updated code...
    Code:
    #include <iostream>
    #include <cstdlib>
    #include <time.h>
    #include <cctype>
    #include <windows.h>
    #include <string.h>
    #include <fstream>
    #include <sstream>
    using namespace std;
    /*
    These constants define our upper
    and our lower bounds. The random numbers
    will always be between 1 and 6, inclusive.
    */
    const int LOW = 1;
    const int HIGH = 12;
    
    string getAddy() // Get the email address from the user...pretty self-explanatory...
    {
           cout << "Enter address below: ";
           string addy;
           getline(cin,addy);
           cout << "\nDid you enter \"" << addy << "\"? [y|n]: ";
           char yn;
           cin >> yn;
           cin.ignore();
           switch ( yn ) {
                  case 'y':
                       break;
                  case 'n':
                       cout << "\nPlease try again." << endl;
                       return getAddy();
                  default:
                          cerr << "\nInvalid selection. Please try again." << endl;
                          return getAddy();
                  }
           return addy;
    }
    
    string randomize()
    {
         string addy = getAddy(); // Puts the value of getAddy into a string
         int len = addy.size(); // Get the length of the string
         string randAddy;                            //
         string usedAddies;                          // 
         ifstream used_addies ("addies.txt");        // Makes sure that no two addies
         while (! used_addies.eof()) {               // generated are the same.
               getline(used_addies, usedAddies); }   //
         used_addies.close();                        //
         stringstream str_randAddy;                  //
         for (int i=1; i < len; i++) {
             if (rand() < HIGH * 0.15) {
                        randAddy[i] = toupper(addy[i]); // Capitilize some random characters
                        }
             }
         str_randAddy << randAddy;
         if (usedAddies.find(str_randAddy.str(), 0) != std::string::npos) { // If it's already been made, start over
                                                 randomize(); }
         return randAddy;
         
    }
    
    void saveAddy() // Save the randomized addy to addies.txt ...again pretty self-explanatory...
    {
         string addy = randomize();
         ofstream addies ("addies.txt", ios::app);
         if (addies.is_open()) {
            addies << addy << ", ";
            addies.close();
            }
            /*
            If there was a problem
            opening the file, terminate
            the program.
            */
         else {
              cerr << "Error: Could not open log file. 10 seconds 'till quit.";
              for (int i=10; i>0; i--) {
                  cout << i << "...\n";
                  Sleep(1000);
                  }
              abort();
              }
         return;
    }
    
    int main()
    {
        getAddy();
        cout << "How many addies are req'd? : "; // tells the program how many addies to generate
        int reqd;
        cin >> reqd;
        cin.ignore();
        for (int i=0; i <= reqd; i++) {
            randomize();
            saveAddy(); }
        cout << "Finished generating addies!!" << endl;
        system("PAUSE");
        return 0;
    }
    looking a bit better; it does getAddy(), then it asks me how many addies I require, but then it just does getAddy() over and over!

  15. #30
    Frequently Quite Prolix dwks's Avatar
    Join Date
    Apr 2005
    Location
    Canada
    Posts
    8,057
    Just something I noticed . . .
    Code:
    string getAddy() // Get the email address from the user...pretty self-explanatory...
    {
           cout << "Enter address below: ";
           string addy;
           getline(cin,addy);
           cout << "\nDid you enter \"" << addy << "\"? [y|n]: ";
           char yn;
           cin >> yn;
           cin.ignore();
           switch ( yn ) {
                  case 'y':
                       break;
                  case 'n':
                       cout << "\nPlease try again." << endl;
                       return getAddy();
                  default:
                          cerr << "\nInvalid selection. Please try again." << endl;
                          return getAddy();
                  }
           return addy;
    }
    If the user does not enter 'y' or 'n' when prompted, shouldn't they enter that again rather than start from the beginning and enter the address? BTW, that doesn't really need to be a recursive function; a loop would work as well.

    Nor does randomize() . . . you like recursive functions, don't you? Ever programmed in LISP?

    Code:
        cout << "How many addies are req'd? : "; // tells the program how many addies to generate
        int reqd;
        cin >> reqd;
        cin.ignore();
        for (int i=0; i <= reqd; i++) {
            randomize();
            saveAddy(); }
    If the user enters 1, two addresses will be generated . . . perhaps you want <, not <=.
    dwk

    Seek and ye shall find. quaere et invenies.

    "Simplicity does not precede complexity, but follows it." -- Alan Perlis
    "Testing can only prove the presence of bugs, not their absence." -- Edsger Dijkstra
    "The only real mistake is the one from which we learn nothing." -- John Powell


    Other boards: DaniWeb, TPS
    Unofficial Wiki FAQ: cpwiki.sf.net

    My website: http://dwks.theprogrammingsite.com/
    Projects: codeform, xuni, atlantis, nort, etc.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. calling functions within functions
    By edd1986 in forum C Programming
    Replies: 3
    Last Post: 03-29-2005, 03:35 AM
  2. writing strings chars from ints
    By deleeuw in forum C++ Programming
    Replies: 20
    Last Post: 08-19-2003, 09:09 AM
  3. fancy strcpy
    By heat511 in forum C++ Programming
    Replies: 34
    Last Post: 05-01-2002, 04:29 PM
  4. Chars - ints
    By MethodMan in forum C Programming
    Replies: 2
    Last Post: 04-15-2002, 08:22 PM
  5. converting chars to ints
    By nebie in forum C++ Programming
    Replies: 6
    Last Post: 09-01-2001, 11:33 AM