while loop problems

#include <iostream>
#include <string>

using namespace std;
//inputData(int& last, int& first&, int& Middle&);
int main()
{
string myString;
cout << "Please enter a string";

getline(cin, myString);

int position = myString.find (' ');
int comma = myString.find (",");
int totalName = myString.length();
int lastName = myString.rfind(' ');
cout << "lastName= " << lastName << endl;
cout << "totalName= " << totalName << endl;
cout << "position= " <<position << endl;
cout << "comma= " << comma << endl;

while (position == lastName)
{
cout << "You need to have one space between each name" <<endl;
getline(cin, myString);

}
while (position == comma)
{
cout << "You need to have a comma in between Last and First name" << endl;
getline(cin, myString);


}


system("PAUSE") ;
return EXIT_SUCCESS;
}
/**************************************************************************
not sure where I having trouble with this one but if I typed in the wrong
information like John,Doe Eric which I am testing to make sure it has two
whitespaces and a comma I dont get past the first loop because when I go to
enter it again the right way John, Doe Eric format then it ask to put in
whitespaces when I have the required whitespaces and loop should be broken.
**************************************************************************/
I'm not quite sure what you're asking, but inside each while loop you never change the value of position, lastName or comma, so the condition of the loop never changes, and execution will never leave the loop.

Oh, and it's best to use code tags: http://cplusplus.com/forum/articles/42672/
I guess I should of clearified better. I am trying to eliminate Garbage in by making sure that if the user inputs without two whitespace then it will go through the loop and check to see if they met the requirements of two whitespaces and one comma when the get.line(cin.myString) gets inputed into the loop I would thought the condition would of changed depending on the user input.

Because if you input for instance John, Doe Eric position should come up with 5 for position and lastName should come up with 8 because of the rfind of the second whitespace. therefore in this case position does not equal lastName. However, if you input John,Doe Eric or even John, DoeEric in both cases for the while loop it would be true and keep telling the user to input First, Last Middle Name in that sequence. Then the next while loop checks for a comma by comparing comma to position if both are equal again the user is asked again to input a comma in this order First, Last Middle Name.

Also, if I don't change the condition in the loop then I have an infinite loop. Here is the code again using the code tags

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
#include <iostream>
#include <string>

using namespace std;
//inputData(int& last, int& first&, int& Middle&);
int main()
{
string myString; 
cout << "Please enter a string";

getline(cin, myString); 

int position = myString.find (' '); 
int comma = myString.find (",");
int totalName = myString.length();
int lastName = myString.rfind(' ');
cout << "lastName= " << lastName << endl;
cout << "totalName= " << totalName << endl;
cout << "position= " <<position << endl;
cout << "comma= " << comma << endl;

while (position == lastName)
{
cout << "You need to have one space between each name" <<endl;
getline(cin, myString);

}
while (position == comma)
{
cout << "You need to have a comma in between Last and First name" << endl;
getline(cin, myString);


}


system("PAUSE") ;
return EXIT_SUCCESS;
}
/**************************************************************************
not sure where I having trouble with this one but if I typed in the wrong 
information like John,Doe Eric which I am testing to make sure it has two 
whitespaces and a comma I dont get past the first loop because when I go to 
enter it again the right way John, Doe Eric format then it ask to put in 
whitespaces when I have the required whitespaces and loop should be broken.
**************************************************************************/ 

Last edited on
Also, if I don't change the condition in the loop then I have an infinite loop. Here is the code again using the code tags

Exactly. And at the moment, you aren't changing the condition in the loop, hence the loop is infinite.

I think you probably want to somehow move your input code inside the loop. And you may need to change the while loop to a do ... while loop in order to allow one request for user input before any checking occurs.
here is what I was suppose to do with this.

Pseudocode:
Main Method
1. Declare a string called myString.
2. Use Call-by-reference pass your string to a method called inputData(); (Hint: uses the &)
3. Use Call-by-value and pass your string to a method called outputData(); (Hint: does not use the &)


inputData Method (Receives string)
1. Get input using cin >> into the string variable you received into this method. (I will be entering my full name in the format of: Last, First Middle.
2. Using the string methods mentioned in this weeks lecture, have your program change the string to: First Middle Initial Last.
3. I would like you to break the string you received apart into 3 separate variables: first, last, middle. (Hint: use find() to find the "," and spaces and use substr() to extract the pieces)
4. Use string concatenation to reassemble the string and overwrite the string you received with the new value.
5. You must use each of the following string methods (at least once): substr(), length(), find(), insert(), erase().
6. Notice the "," is missing out of the name.

outputData Method (Receives string)
1. Output the new string to the screen using cout <<.
2. Comments are required, but pseudocode or flowchart are not.
3. All Input/Output should be done using the standard C++ library string class.
4. Include: system("PAUSE"); after your output to pause the screen.

with the code provided I was trying to make sure the user input was accurate. Where I have a problem is doing the call by reference which I understand requires an & but how is the part I guess I am trying to ask.

PS I fixed the loop saw that it wasn't in the look like you said after posting

This is what I got thus far:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
#include <iostream>
#include <string>

using namespace std;/*
void inputData(string& first, string& middle, string& last)
{
     last =" " ;
     first =" " ;
     middle =" " = midddle.erase(1); 
}
     */
int main()
{
string myString; 
              
    cout << "Please enter your Last, First Middle Name" << endl;
    cout << endl;
    cout << endl;
       
    getline(cin, myString); 
    
      int comma = myString.find (","); // use this to make sure comma is equal to reversecomma since there can only be one comma
      int reversecomma = myString.rfind(","); //to compare with comma
      int totalName = myString.length(); // get the over all lenght
      int firstSpace = myString.find(' '); // this finds the first space I was using rfind to find the second but found if there 
      int secondSpace = myString.find(' ', firstSpace + 1);// is a third white-space it still would include it when finding.
      int thirdSpace = myString.find(' ', secondSpace + 1); // this is to test if when inputted someone hits the spacebar afterwords
       
  
           while ((comma != reversecomma)  || ((reversecomma + 2)>= secondSpace) || (firstSpace == 0) || (thirdSpace != -1))
           {//Here I begin testing inputs to see if accurate notice comma has to equal reversecomma if not starts loop then I use
           //reversecomma which measures from the end to beginning and add 2 to the int which is how many spaces it should include
           // firstSpace happens if someone puts a space before last name
           // finally thirdSpace is to test to see if there is any spaces after Middle name.
                 cout << "You need to have a comma in between Last and First name only" << endl;
                 cout << "For example Doe, John Ericson or you may have to many white-spaces" << endl;
                 cout << "Please try again enter Last, First Middle Name" << endl;
                 getline(cin, myString); 
                 
                 
                 comma = myString.find (",");
                 reversecomma =myString.rfind(",");
                 totalName = myString.length();
                 firstSpace = myString.find(' ');
                 secondSpace = myString.find(' ' , firstSpace + 1);
                 thirdSpace = myString.find(' ', secondSpace + 1);
           }      
    // now that it as gone through the checks to make sure information is accurate I can begin setting up container so I will need 
    // prototype this is located before Main();
  
   string b = myString.substr(0, comma);
   b.insert(0, " ");
   cout << b << endl;
   string a = myString.substr(firstSpace , (secondSpace - firstSpace));
   cout << a << endl;
   cout << firstSpace << endl << secondSpace << endl << totalName << endl;
   string c = myString.substr(secondSpace + 1, (totalName - secondSpace)+ 1);
   c.insert(0, " ");
   
   cout << a << b << c << endl;
  
    
    
    
    cout << endl;
    cout << endl;
    
    system("PAUSE") ;
    return EXIT_SUCCESS;
}
Last edited on
Have you read this website's tutorial on passing by reference?
http://www.cplusplus.com/doc/tutorial/functions2/
(the top bit)

Let me know how you get on with that tutorial!
Yes I have read this article but I am not sure how to implement it into this program.
if you look at the commented out section I tried to implement it unsuccessfully.
Also this program insures that the input is exactly right. So that I can utilize it.
1
2
3
4
5
6
void inputData(string& first, string& middle, string& last)
{
     last =" " ;
     first =" " ;
     middle =" " = midddle.erase(1); 
}


The function header is correct. The function receives three references to strings, which can then be used to modify the strings and access their existing values.

Now just do whatever you want to those strings within the function. Then, in main, you create some strings, and pass them as arguments. When the function returns, the strings' values will retain the values given to them in inputData because they were passed by reference.
suppose I wanted to erase the everything but the beginning of the middle name? comming out of my prototype like the one above how would I do it.
where would call by value come into play?
Firstly, I have just noticed in your code: middle =" " = midddle.erase(1);
This tries to assign the value of middle.erase(1) to the string literal " ". Clearly this is not allowed. What exactly were you intending this line to do?

Are you asking how to erase from the string? That will be in the string documentation:
http://cplusplus.com/reference/string/string/
If you pass it by reference, changes in the called function will happen to the variable in the caller function as well.

Call by value means that the values are copied when passed to the function, whereas call by reference means they are not copied. Use call by value when passing intrinsic types and you don't want to change the caller's values. Use call by reference if you do want to change the caller's value. If you are passing a large structure such as a string and you don't want to change it, pass it by const reference to save expensive copy operations.
What I was trying to do is erase everything except the beginning letter of the middle name. middle =" " = midddle.erase(1); after it comes out of the call by reference. According to how the program is suppose to be written I am suppose to:
2. Use Call-by-reference pass your string to a method called inputData(); (Hint: uses the &)
3. Use Call-by-value and pass your string to a method called outputData(); (Hint: does not use the &)

but not sure how the call by value comes into play. I can see the call by reference which is like a place holder or container that holds the string sort of like an array but limited.

I know that call by value takes a numerical value whether it is a numerical value of the ASCII standard or the input value.

but like I said not sure where the call by value comes into play see above.
Last edited on
Here is what I was thinking...
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
#include <iostream>
#include <string>

using namespace std;
void inputData(string& first, string& middle, string& last)
{
     first.substring()
     middle.erase(2)
     last.substring()
}
     
int main()
{
string myString; 
              
    cout << "Please enter your Last, First Middle Name" << endl;
    cout << endl;
    cout << endl;
       
    getline(cin, myString); 
    
      int comma = myString.find (","); // use this to make sure comma is equal to reversecomma since there can only be one comma
      int reversecomma = myString.rfind(","); //to compare with comma
      int totalName = myString.length(); // get the over all lenght
      int firstSpace = myString.find(' '); // this finds the first space I was using rfind to find the second but found if there 
      int secondSpace = myString.find(' ', firstSpace + 1);// is a third white-space it still would include it when finding.
      int thirdSpace = myString.find(' ', secondSpace + 1); // this is to test if when inputted someone hits the spacebar afterwords
       
  
           while ((comma != reversecomma)  || ((reversecomma + 2)>= secondSpace) || (firstSpace == 0) || (thirdSpace != -1))
           {//Here I begin testing inputs to see if accurate notice comma has to equal reversecomma if not starts loop then I use
           //reversecomma which measures from the end to beginning and add 2 to the int which is how many spaces it should include
           // firstSpace happens if someone puts a space before last name
           // finally thirdSpace is to test to see if there is any spaces after Middle name.
                 cout << "You need to have a comma in between Last and First name only" << endl;
                 cout << "For example Doe, John Ericson or you may have to many white-spaces" << endl;
                 cout << "Please try again enter Last, First Middle Name" << endl;
                 getline(cin, myString); 
                 
                 
                 comma = myString.find (",");
                 reversecomma =myString.rfind(",");
                 totalName = myString.length();
                 firstSpace = myString.find(' ');
                 secondSpace = myString.find(' ' , firstSpace + 1);
                 thirdSpace = myString.find(' ', secondSpace + 1);
           }      
    // now that it as gone through the checks to make sure information is accurate I can begin setting up container so I will need 
    // prototype this is located before Main();
  
   string c = myString.substr(0, comma);
   c.insert(0, " ");
   
   string a = myString.substr(firstSpace , (secondSpace - firstSpace));
   
   
   string b = myString.substr(secondSpace + 1, (totalName - secondSpace)+ 1);
   b.insert(0, " ");
   
   cout << a << b << c << endl;
  inputData(a, b, c)
    
    
    
    cout << endl;
    cout << endl;
    
    system("PAUSE") ;
    return EXIT_SUCCESS;
}


but not compiling
Several of your lines (7-9, 61) are missing their terminating semicolons. Fix that, and if you still have compiler errors, can you tell me what they say?
In function `void inputData(std::string&, std::string&, std::string&)':
7 'struct std::basic_string<char, std::char_traits<char>, std::allocator<char> >' has no member named 'substring'
9 'struct std::basic_string<char, std::char_traits<char>, std::allocator<char> >' has no member named 'substring'
Right, because string has no member called 'substring'. It does, however, have a function called 'substr', which is probably what you're looking for.
Topic archived. No new replies allowed.