Recursion in simple function - c++

I am having the following function:
void test(const char *nap){
if (*nap != 'D'){
test(nap+1);
std::cout << *nap;
}};
When I call the function with:
"ABCD"
Output, that I thought I would get was: ABC, however, in reality, its CBA. Can anyone explain to me where do I make mistake?

You call it in the wrong order. Revert that:
test(nap+1);
std::cout << *nap;
like this
std::cout << *nap;
test(nap+1);

Your recursion is to go to the end of the text string and to then go backwards printing each character.
In other words your function keeps calling itself until it reaches end of string. At that point it returns to where it called itself and the next step is to print the current character.
Then you return to where it called itself again and the next step is to print the current character.
The result is that you traverse the string until the end of string by the recursive calls. Once you reach the end of string you start unwinding the series of recursive calls. At each return you print the current character.
Try the following which will print the current character and then call itself to print the next character instead. When it reaches the end of the string it will unwind the recursive calls.
void test(const char *nap) {
if (*nap != 'D'){
std::cout << *nap;
test(nap+1);
}
};

because the std::cout is after calling the recursion ( )..
test(nap+1);
std::cout << *nap;
That is parent feeds children before eating.
The below will get what you want:
std::cout << *nap;
test(nap+1);

Related

Removing end of a line after calling a void function

I have a void function that recursively prints an AVL tree in order, using a comma and a space between every key.
After the void function is called, I want to remove the last comma and space, but I am not sure how. I tried doing std::cout << '\b' << '\b', but it doesn't do anything.
What I'm trying is something like:
void printInoder(root){
InorderHelper(root);
cout << '\b' << '\b' << endl;
}
The name backspace is a bit misleading. It doesn't print a space.
If the output ends with , you probably want std::cout << "\b\b \b\n";. That is, step two steps back, print a space over the , and then step one step back. Since you do a newline last, the last \b can be omitted.
std::cout << "\b\b \n";
It would probably be better to fix it at the source and not print the characters you want to erase at all.

C++ variable appears to have different values in different functions

This is a simplified and more informative version of a question that has now been deleted.
BACKGROUND
I am currently trying to familiarize myself with basic C++ programming and decided to make a game of hangman. However, I noticed that an integer variable called preset_count—which is meant to count how many letters have been pre-guessed by the game— always returns a value of 0 in the main() function whereas in other functions, it has a value of 2 (or anything greater than 0).
What I am trying to accomplish here is that the program will automatically fill in the vowels of the word the player is trying to guess. Depending on how many vowels are filled in, the score the player gets when guessing a character right increases.
For example, the player is trying to guess the word "eraser," so the hangman program will print out
"e _ a _ e _ " they will gain 334 points if they guess correctly.
In a word like "circle," though (which will be printed as "_ i _ _ _ e ") the player will gain 250 points per guess because of the fact that the player has to guess 4 characters instead of 3.
THE ISSUE AND CODE
In order to accomplish this, I added code meant to count how many vowels have been filled in by the game in a special function.
The code below is a simplified version of the one in the actual hangman program that re-creates the issue I have with the program. See, the game outputs a different value of the preset_count value in each function.
Essentially, the main() function has a
cout << "preset_count in main(): " << preset_count;
//This line of code prints out 0. However, the variant of this in find_preset():
cout << "preset_count in find_preset(): " << preset_count;
//Which, on the other hand, prints out 3.
Is there any reason behind these contradictory variable reports? Is there any way to solve this?
#include <iostream>
using namespace std;
void find_preset (int, const string, string); //Prototyping for find_preset()
int main() {
int preset_count = 0; //Amount of times a character in PRESET_LETTERS appears in the word variable.
const string PRESET_LETTERS = "AEIOUaeiou"; //The letters the program is looking out for.
string word = "eraser"; //The word being analyzed.
cout << "\nmain(): main() executed, variables declared, about to execute find_preset() function.";
find_preset(preset_count, PRESET_LETTERS, word); //find_preset() function; finds how many PRESET_LETTERS characters are in word.
cout << "\nmain(): find_preset() finished executing.\n"; //Announces that find_preset() function finished executing.
cout << "\n\nDEBUG word: " << word << endl; //Report on the set word value.
cout << "DEBUG preset_count in main(): " << preset_count << endl << endl; //Report on preset_count's value in main().
//This is where my issue takes place in. This reports a value whereas in find_preset(), the value of preset_count is 2.
return 0;
}
//find_preset() function; finds how many PRESET_LETTERS characters are in word.
void find_preset(int preset_count, const string PRESET_LETTERS, string word) {
int word_index = 0; //How many characters of word that find_preset() has gone through.
cout << "\nfind_preset() executed, now counting amount of instances of PRESET_LETTERS in word.";
//While word_index is less than the size of word. While the entire word variables hasn't been scanned yet.
while (word_index < word.size()) {
//If a PRESET_LETTERS character is found in word.
if(word.find(PRESET_LETTERS)) {
preset_count++; //preset_count increased by 1.
cout << "\nfind_preset(): preset_index and preset_count increased by 1."; //Reports preset_count++; has been executed.
}
word_index++; //Word index increased by 1.
cout << "\nfind_preset(): word_index increased by 1."; //Reports that word_index++; has been executed.
}
cout << "\nfind_preset(): while (word_index < word.size()) finished executing, now printing debug menu for find_preset().\n";
//Reports that the while loop has finished executing.
cout << "\n\nDEBUG: preset_count in find_preset(): " << preset_count; //Report on preset_count's value in find_preset().
//This is also where my issue takes place in. This reports that preset_count's value is 2 whereas in main, it reports 0.
cout << "\nDEBUG: word_index value: " << word_index << endl << endl; //Report on word_index's value.
}
The arguments in C++ are copies of what are passed by default. Therefore, modifications of arguments in callee functions won't affect what are passed in caller. You should add & to make the arguments to references if you want to have functions modify what are passed.
Both declaration and definition should be modified.
void find_preset (int&, const string, string); //Prototyping for find_preset()
void find_preset (int& preset_count, const string PRESET_LETTERS, string word) //find_preset() function; finds how many PRESET_LETTERS characters are in word.
{

Program throwing exception

I am writing a program that allows the user to enter a sentence which then gets stored in a string and then the program will remove any full stops in the sentence and then create a list of each individual word in the string before outputting that list to the console.
the program is working perfectly as long as there is only 1 full stop in the sentence but if there are any more than that it throws this exception:
Unhandled exception at at 0x7696B727 in Project6.exe: Microsoft C++ exception: std::out_of_range at memory location 0x0022F8B8.
and then if I continue to run it it throws:
Run-Time Check Failure #0 - The value of ESP was not properly saved across a function call. This is usually a result of calling a function declared with one calling convention with a function pointer declared with a different calling convention.
any suggestions? (and before anyone asks, i know you usually only have 1 full stop in a sentence but i need to do it with more than 1 as part of testing.
here is the code:
#include <iostream>
#include <string>
using namespace std
string sSentence; // sets up a string variable called sSentence
int i = 0;
void RemoveFullStop()
{
while(sSentence.find (".") != string::npos) // the program runs this loop until it cannot find any more full stops in the string
{
i = sSentence.find("." , i); // find the next full stop in the string and get the character count of the space and place it in the variable i
sSentence.replace(i,1,""); // remove the full stop
}
}
void ListWords()
{
while(sSentence.find (" ") != string::npos) // the program runs this loop until it cannot find any more spaces in the string
{
i = sSentence.find(" " , i); // find the next space in the string and get the character count of the space and place it in the variable i
// cout << i << endl; // output the contents of iWordSpace to the console (used for debugging - no longer used)
sSentence.replace(i,1,"\n");
// cout << sSentence << endl; // output the contents of iWordSpace to the console (used for debugging - no longer used)
}
}
int main()
{
getline(cin, sSentence); // get user input and store it in sSentence (using the getline function so the .find operation works correctly)
RemoveFullStop(); // calls the RemoveFullStop void function that removes all full stops from the string
ListWords(); // calls the ListWords void function that splits the string into a list of words
cout << endl; // formatting line
cout << "The words that were in the sentence were:" << endl;
cout << endl; // formatting line
cout << sSentence << endl;
cout << endl; // formatting line
system("pause");
return 0;
}
The problem is that you keep re-using i, in both RemoveFullStop and ListWords.
i only ever increases, and so eventually it can get past the end of the string.
You really shouldn't need a global i variable at all, to do this task.
The reason this happens is that when sSentence.find(" " , i) in ListWords runs, i's value is not 0 because it was already defined in RemoveFullStop(). To fix this, first remove int i = 0;, then add it to RemoveFullStop() and ListWords()
Also, while this is just a style thing and won't effect your codes ability to run, I wouldn't call this variable i as i,j,k usually imply counters. Call this variable something more appropriately descriptive.
Here is the relevant code as it should be.
using namespace std
string sSentence;
void RemoveFullStop()
{
int charPlace = 0;
while(sSentence.find (".") != string::npos)
{
charPlace = sSentence.find("." , charPlace);
sSentence.replace(charPlace,1,"");
}
}
void ListWords()
{
int charPlace = 0;
while(sSentence.find (" ") != string::npos)
{
charPlace = sSentence.find(" " , charPlace);
sSentence.replace(charPlace,1,"\n");
}
}

Why is this simple program giving a segmentation fault?

I have written a simple C++ program. The idea is, once it sees a non-alphabetic character, then till the time it see a new word (a blank) or the string ends, it keeps on incrementing the iterator.
This generates Segmentation fault, no idea why :(
Please help.
#include <iostream>
using namespace std;
int main()
{
string str("Hello yuio");
string::iterator it=str.begin();
while(it!=str.end())
{
cout << *it << endl;
if(isalpha(*it)==0){
cout << *it << ":Is not an alphabet\n";
while((*it!=' ')||(it!=str.end()))
{
cout << *it << endl;
it++;
}
}
if(it!=str.end()){it++;}
} // while loop ends
} // End of main
while((*it!=' ')||(it!=str.end()))
*it is evaluated before checking if it itself is ok to use. Change to:
while((it!=str.end())&&(*it!=' '))
while((*it!=' ')||(it!=str.end()))
The line above contains two errors.
The condition says that the loop shall go on while the current character is not a space OR end of string is not reached yet. I.e., even when the end is reached but current char is not a space, the loop will proceed.
Once you fixed this error (by replacing || with &&), you still try to dereference the end iterator (because the check for space comes before the check for end of string), which is not allowed. You have to switch the order of conditions:
while((it!=str.end()) && (*it!=' '))
The problem is here:
while((*it!=' ')||(it!=str.end()))
When you reach the end of the string, the first part of the condition is true and so you continue looping and incrementing the iterator.
You need to replace with &&:
while((*it!=' ')&&(it!=str.end()))

not working function with no errors

I've implemented a function to display an avl tree after inserting nodes into it like this
template<class nodetype>
void AVLtree<nodetype>::display() const
{
display(Proot);
}
template<class nodetype>
void AVLtree<nodetype>::display(Node<nodetype> * ptr) const
{
if(ptr==0)
return ;
cout<<ptr->value<<" ";
display(ptr->Pleft);
display(ptr->Pright);
}
after compiling,there were no errors ,the program worked but nothing were printed on the screen
help me please....!!
thanks
(Assuming that your tree is built correctly). Screen output is normally line-buffered. You need to output std::endl to std::cout (or at least '\n' character) for something to appear on the screen.
Of course, if your tree is built incorrectly, the root pointer might be null and nothing would be printed for obvious reasons (just a guess).
Finally, even if your tree is built correctly, but all data (ptr->value) is, say, just strings that are empty (for example) or contain only whitespace, then no wonder you can't see anything on the screen.
One technique I like to use is to add delimiters around debug strings:
cout << "-->" << ptr->value << "<--" << endl;
That way, it's easy to distinguish empty output from no output.
You may also want to add something that shows when your entire tree is empty:
void AVLtree<nodetype>::display() const
{
if (Proot)
display(Proot);
else
cout << "empty tree" << endl;
}
If you are printing on a console window, this function may be of use:
void Pause(void)
{
cout << "\nPaused, press ENTER to continue.\n";
cin.ignore(10000, '\n');
return;
}
Call this function before any exit methods or return statements in main.
first of all you need a conceptual overhaul.. Who told you you can compare ptr with 0 ?
Are you trying to suggest that a pointer if nullified is equal to 0 ? Thats totally wrong .. try this :
#include<iostream>
#include<conio.h>
using namespace std;
int main () {
int *p = NULL ;
cout<<*p<<endl;
getch();
return 0;
}
and there your program crashes ... compare ptr with NULL instead of 0 ..