I'm new to both this forum and Visual C++ so let me know if I pull a forum no-no.
I try all the exercises as I go through the book and sometimes embellish them to improve my understanding of various C++ features.
Chap 3 Exercise 2 asks you to:
Write an ISO/IEC C++ program to read characters from the keyboard and count the vowels. Stop counting when a Q (or a q) is encountered. Use a combination of an indefinite loop to get the characters, and a switch statement to count them.
Then Exercise 5 asks you to write a CLR version of the program.
Here's the CLR version of my program, the ISO/IEC program worked without a problem.
Code:
// Ch3_Exercise_2.cpp : main project file.
#include "stdafx.h"
using namespace System;
int main(array<System::String ^> ^args)
{
int vowels(0);
int consonants(0);
wchar_t letter;
Console::Write("This program keeps a running total of vowels and consonants that you input.\n");
Console::Write("It stops counting when you enter a q or Q.\n\nEnter a letter at the ? prompt.\n\n");
do
{
start: Console::Write(L"? "); // Prompt for input
letter = Console::Read(); // Read input character
letter = Char::ToUpper(letter); // Convert to a capital letter
if(letter == 'Q') // Check for input of q or Q
{
Console::WriteLine(L"You have entered a total of {0} vowels and {1} consonants.", vowels, consonants); // Output number of vowels and consonants entered
Console::ReadLine(); // Added to halt so you can read the statement directly above. Ignored if line 19 is ommited.
return 0; //Terminate if q or Q
}
if(!((letter >= 'A') && (letter <= 'Z'))) // Test for non-letter
{
Console::WriteLine(L"That was not a letter. Please try again. Letter = 0x{0:x}", safe_cast<int>(letter)); // Output not a letter and output Hex value of letter
goto start; // Return to inputting characters
}
switch(letter*((letter >= 'A') && (letter <= 'Z'))) //Setup switch to parse for vowels / consonants
{
case 'A': case 'E': case 'I': case 'O': case 'U':
++vowels; //Increment vowels for case A,E,I,O,U
Console::WriteLine(L" Added one to vowels");
break;
default: ++consonants; //Increment consonants for case letter != A,E,I,O,U
Console::WriteLine(L" Added one to consonants");
break;
}
}
while(true); // Continuous loop
return 0;
}
For which I get an output of:
This program keeps a running total of vowels and consonants that you input.
It stops counting when you enter a q or Q.
Enter a letter at the ? prompt.
? a
Added one to vowels
? That was not a letter. Please try again. Letter = 0xd
? That was not a letter. Please try again. Letter = 0xa
? s
Added one to consonants
? That was not a letter. Please try again. Letter = 0xd
? That was not a letter. Please try again. Letter = 0xa
? 1
That was not a letter. Please try again. Letter = 0x31
? That was not a letter. Please try again. Letter = 0xd
? That was not a letter. Please try again. Letter = 0xa
? q
You have entered a total of 1 vowels and 1 consonants.
QUESTIONS:
1) Where did the
? That was not a letter. Please try again. Letter = 0xd
and
? That was not a letter. Please try again. Letter = 0xa come from?
2)
0xd and
0xa are not hex representations while the
0x31 is correct. What's going on here?
3) I thought that the
{0:X} format automatically added the
0x to the output without you having to add it.
4) The last line of output flashes by in milliseconds because the
Console::ReadLine() is ignored.
In a totally serendipitous action I put a
Console::ReadLine() statement after the
letter = Console::Read() line.
VOILA!!!
The program works properly. Even the
Console::ReadLine() at the end now works.
The code is now:
Code:
// Ch3_Exercise_2.cpp : main project file.
#include "stdafx.h"
using namespace System;
int main(array<System::String ^> ^args)
{
int vowels(0);
int consonants(0);
wchar_t letter;
Console::Write("This program keeps a running total of vowels and consonants that you input.\n");
Console::Write("It stops counting when you enter a q or Q.\n\nEnter a letter at the ? prompt.\n\n");
do
{
start: Console::Write(L"? "); // Prompt for input
letter = Console::Read(); // Read input character
Console::ReadLine(); // ********The mystery line that makes it work*********
letter = Char::ToUpper(letter); // Convert to a capital letter
if(letter == 'Q') // Check for input of q or Q
{
Console::WriteLine(L"You have entered a total of {0} vowels and {1} consonants.", vowels, consonants); // Output number of vowels and consonants entered
Console::ReadLine(); // Added to halt so you can read the statement directly above. Ignored if line 19 is ommited.
return 0; //Terminate if q or Q
}
if(!((letter >= 'A') && (letter <= 'Z'))) // Test for non-letter
{
Console::WriteLine(L"That was not a letter. Please try again. Letter = 0x{0:x}", safe_cast<int>(letter)); // Output not a letter and output Hex value of letter
goto start; // Return to inputting characters
}
switch(letter*((letter >= 'A') && (letter <= 'Z'))) //Setup switch to parse for vowels / consonants
{
case 'A': case 'E': case 'I': case 'O': case 'U':
++vowels; //Increment vowels for case A,E,I,O,U
Console::WriteLine(L" Added one to vowels");
break;
default: ++consonants; //Increment consonants for case letter != A,E,I,O,U
Console::WriteLine(L" Added one to consonants");
break;
}
}
while(true); // Continuous loop
return 0;
}
With an output of:
This program keeps a running total of vowels and consonants that you input.
It stops counting when you enter a q or Q.
Enter a letter at the ? prompt.
? a
Added one to vowels
? A
Added one to vowels
? s
Added one to consonants
? S
Added one to consonants
? 1
That was not a letter. Please try again. Letter = 0x31
? @
That was not a letter. Please try again. Letter = 0x40
? q
You have entered a total of 2 vowels and 2 consonants.
Which is what is expected.
SO! Why is the added
Console::ReadLine() needed and whats going on without it?
The book says to avoid using
goto statements. Any suggestions on how to modify my program to avoid this?
Any insight or other comments would be greatly appreciated.
Also is there a way to copy command line text rather than just re-typing it?
Thanks.