Big O of Switch statement having function calls in its Cases? - c++11

How can we calculate Big O of switch statement whom are having function calls in there cases. that Function can be the Function in whom the switch statement is present and can also direst to another function whom can send it back to the same Switch statement.
void ifpascorrectSwitch(int *currentbalance) {
cout << "\n\n";
cout << "Current balance = £" << *currentbalance << endl;
string casee;
cout << "Enter any of the below option\n"
"1 for Deposit cash \n"
"2 for Withdraw cash\n"
"e for Quiting the application\n"
"= ";
cin >> casee;
if (casee.length() == 1) {
const char *k = casee.c_str(); // character inter to a c string
switch (*k) {
case '1':
cout << "1 Deopist cash \n";
Depositcash(currentbalance);
//Deposit is another function call whom can can come back to this function
// and have this switch menu again because of bellow given //ifpascorrectSwitch(currentbalance) which is function call of the current //function
ifpascorrectSwitch(currentbalance);
break;
case '2':
cout << "2 Withdraw menu\n";
WithdrawCash(currentbalance);
ifpascorrectSwitch(currentbalance);
break;
case 'e':
cout << "r is working";
break;
default:
cout << "Default switch wrong entery";
ifpascorrectSwitch(currentbalance);
break;
}
} else {
cout << "Wrong entery please try again";
ifpascorrectSwitch(currentbalance);
} }
All other function call other then ifpascorrectSwitch(currentbalance)which is current function call are having same scenario of switch stament. almost.
If only someone could help me atleast undesrtanding this Switch statement Big O calcultaion.

Related

Serial Communication data problem between Windows and embedded System (STM32) (C/C++)

I currently try to set up communication between a Windows program and a µC.
I'll show you the code to initialize the port:
int serialCommunication::serialInit(void){
//non overlapped communication
hComm = CreateFile( gszPort.c_str(),
GENERIC_READ | GENERIC_WRITE,
0,
0,
OPEN_EXISTING,
0,
0);
if (hComm == INVALID_HANDLE_VALUE){
cout << "Error opening port." << endl;
return 0;
}
else{
cout << "Opened Port successfully." << endl;
}
if (SetCommMask(hComm, EV_RXCHAR) == FALSE){
cout << "Error setting communications mask." << endl;
return 0;
}
else{
SetCommMask(hComm, EV_RXCHAR);
cout << "Communications mask set successfully." << endl;
}
if (GetCommState(hComm, &dcbSerialParams) == FALSE){
cout << "Error getting CommState." << endl;
return 0;
}
else{
GetCommState(hComm, &dcbSerialParams);
cout << "CommState retrieved successfully" << endl;
}
dcbSerialParams.BaudRate = CBR_115200; // Setting BaudRate = 115200
dcbSerialParams.ByteSize = 8; // Setting ByteSize = 8
dcbSerialParams.StopBits = ONESTOPBIT; // Setting StopBits = 1
dcbSerialParams.Parity = NOPARITY; // Setting Parity = None
if (SetCommState(hComm, &dcbSerialParams) == FALSE){
cout << "Error setting CommState" << endl;
return 0;
}
else{
SetCommState(hComm, &dcbSerialParams);
cout << "CommState set successfully" << endl << endl;
cout << "+---CommState Parameters---+" << endl;
cout << "Baudrate = " << dcbSerialParams.BaudRate << endl;
cout << "ByteSize = " << static_cast<int>(dcbSerialParams.ByteSize) << endl; //static Cast, um int auszugeben und kein char
cout << "StopBits = " << static_cast<int>(dcbSerialParams.StopBits) << endl; //static Cast, um int auszugeben und kein char
cout << "Parity = " << static_cast<int>(dcbSerialParams.Parity) << endl; //static Cast, um int auszugeben und kein char
cout << "+--------------------------+" << endl;
}
/*------------------------------------ Setting Timeouts --------------------------------------------------*/
timeouts.ReadIntervalTimeout = 50;
timeouts.ReadTotalTimeoutConstant = 50;
timeouts.ReadTotalTimeoutMultiplier = 10;
timeouts.WriteTotalTimeoutConstant = 50;
timeouts.WriteTotalTimeoutMultiplier = 10;
if (SetCommTimeouts(hComm, &timeouts) == FALSE){
cout << "Error setting timeouts" << endl;
return 0;
}
else{
SetCommTimeouts(hComm, &timeouts);
cout << "Timeouts set successfully." << endl;
cout << "+--------------------------+" << endl;
return 1;
}
My Read function looks like this:
void serialCommunication::serialRead(void){
bool readStatus;
bool purgeStatus = 0;
bool correctData = 0;
cout << "Waiting for Data..." << endl; // Programm waits and blocks Port (like Polling)
readStatus = WaitCommEvent(hComm, &dwEventMask, 0);
if (readStatus == FALSE){
cout << "Error in setting WaitCommEvent." << endl;
}
else{
cout << "Data received." << endl;
do{
readStatus = ReadFile(hComm, &TempChar, sizeof(TempChar), &NoBytesRead, 0);
SerialBuffer += TempChar; // add tempchar to the string
}while (NoBytesRead > 0);
SerialBuffer.pop_back(); // Delete last sign in buffer, otherwise one "0" too much shows up, for example "23900" instead of "2390"
cout << endl << SerialBuffer << endl;
SerialBuffer = ""; // Reset string
}
So at some point, my µC sends the String "Init complete...!\r\n" after initializing some things. This works well.Init complete proof
Now after that, the communcation produces errors. I am getting Data I should not receive. The µC can only send data, if a specific string is sent to it by the PC. While debugging I could detect, that the µC never receives this specific string and therefore never sends data. In the following picture, I show you what gibberish I am receiving constantly though.
Receiving Gibberish
/EDIT: I am constantly receiving the same gibberish
The funny thing is, I even receive that data, when the µC is completely switched off (Serial Cables are still connected). So there has to be some data at the port, which just is not deleted. I tried to restart the PC aswell, but it didn't help either.
I will also show you my while loop on PC:
while (testAbbruch != 1){
pointer = acMessung(anzahlMessungen, average); // measurement with external multimeter
cout << endl;
cout << "Average: " << average << endl << endl;
if (average >= 30){
testAbbruch = 1; // there won't be a next while iteration
befehl = "stopCalibration\r\n";
serialTest.serialWrite(befehl);
serialTest.serialRead();
}
else{
cout << "Aktion: ";
std::getline (cin, befehl);
befehl = "increment"; //for debugging
if (befehl == "increment"){
befehl.append("\r\n"); // adding it, so the µC can detect the string correctly
serialTest.serialWrite(befehl);
serialTest.serialRead(); // µC has to answer
}
else if(befehl == "decrement"){
befehl.append("\r\n"); // adding it, so the µC can detect the string correctly
serialTest.serialWrite(befehl);
serialTest.serialRead(); // µC has to answer
}
befehl = ""; // string leeren für nächsten Aufruf
}
}
I know my program is far from perfect, but if I understood the serial Communication with Windows correctly, the buffer is deleted while reading.
Is there any clue you could give me?
EDIT// I just wrote a program that expects one of two inputs: One input is called "increment" the other one is called "decrement". Those inputs are sent to the µC via the serial communication port. Every time I try to send "increment" and instantly after that I am reading from the port, I receive the weird data from this picture. Now, every time I try to send "decrement" and instantly after that I am reading from the port, I receive the weird data from that picture.
//
So my guess is that the data somehow is changed and then looped back to the PC? But why and how?!

why does my code skip the if statement and go to the else when i open the file

my assignment asks me to open a file, but if it doesn't open you are given 3 tries, but when I input the correct file on my second and third try it still give me the error I wrote 'ERROR: File " << input_filename << " could not be opened for input"' and goes to my else statement
char input_filename[90];
ifstream input;
cout << "Type the name of the input file which will hold the simulation results : " << endl;
cin>> input_filename;
input.open(input_filename);
if (input.fail())//if the file doesn't open it will go to the do while loop error message
{
int i = 0;
int h = 0;
do
{
cout << "ERROR: File " << input_filename << " could not be opened for input" << endl;
cin >> input_filename;// allows user to reinput filename
input.open(input_filename);//opens file
if ( !input.fail())
{
cout << "if statement" << endl;
h++;// if h doesn't equal 1 it goes out of the loop
}
else
{
cout << "else statement" << endl;
i++;//post-decrement allows for 2 more tries to input file
}
if (i >= 2)
{
cout << "ERROR: You exceeded maximum number of tries allowed" << endl;
cout << "while entering the input file name" << endl;
return 1;// return 1 represents the error of the input not opening after the 3rd time of inputing
}
} while (i < 2 && h != 0);// do while because it need to be a post condition for two varibles
}
If you reach line 106, it implies your file input succeeded. At that line you should NOT increment h. In fact you should leave h at zero if you want to break out of the loop (Assuming the file input worked).

Isalpha() function with while loop c++

I want to create a while loop that will allow me to input a mix of string numbers until I input string that contains all characters.
Also, I have a problem with output
int main() {
string name;
string temp;
cout << "Enter your name:";
cin >> name;
cout << endl;
for(auto a:name) {
if(isalpha(a)) {
temp=name;
} else {
while(!isalpha(a)) {
cout << "Enter your name without digit:";
cin >> name;
cout << endl;
}
}
}
cout << temp << endl;
}
for(auto a:name) {
This is a loop over the characters in name, as entered after the prompt "Enter your name:". The current character is assigned to a.
if(isalpha(a)) {
temp=name;
}
If the letter is alphabetic, assign temp = name (every time the current letter is alphabetic... this is not what you want!).
else {
...if the current character (a) is not alphabetic...
while(!isalpha(a)) {
...enter a second loop, which will loop until a is alphabetic...
cout << "Enter your name without digit:";
cin >> name;
cout << endl;
}
...but a is never again assigned to. Your loop does not terminate.
You should re-work your logic. As this looks like a self-study project, I will not write the reworked loop for you, as I think you will learn much more from trying to do it on your own.

while loop continues after sentinel value is reached

I'm currently confused on while loops, specifically why the loop still runs everything else in the loop specifically after the sentinel value is reached...
here's the example of my code below:
while (quit != -1) {
cout<<"Options: a)ir; w)ater; s)teel; q)uit \n";
char option=' ';
cin>>option;
option = toupper(option);
while( option != 'A' && option != 'W' && option != 'S' && option != 'Q'){
cin.clear();
cout<<"INVALID INPUT!! \n";
cin>>option;
option = toupper(option);
}
switch(option){
case 'Q':
cout<<"You Have Quit!";
quit = -1;
break;
}
cout<<"Please input the distance: \n";
double distance=0;
cin>>distance;
while(distance < 0){
cin.clear();
cout<<"INVALID INPUT \n";
cin>>distance;
}
switch(option){
case 'A':
seconds = distance/speed_a;
cout<< "Time travled: " << setprecision(2) << fixed << seconds << "\n";
break;
case 'W':
seconds = distance/speed_w;
cout<< "Time travled: " << setprecision(2) << fixed << seconds << "\n";
break;
case 'S':
seconds = distance/speed_s;
cout<< "Time travled: " << setprecision(2) << fixed << seconds << "\n";
break;
}
}
basically when the user enters the 'q' character it runs the quit switch statement... it does quit the loop but it still asks for the distance traveled before ending the loop..
output is shown below:
Options: a)ir; w)ater; s)teel; q)uit
q
You Have Quit!
Please input the distance:
0
--------------------------------
Process exited after 2.944 seconds with return value 0
Press any key to continue . . .
is there any way to edit the code so it immediately quits the loop or is this just the way all loops are pre-programmed?
any advice would be appreciated
The break statement Inside a switch case only exits the switch block, not the outer while loop. Your code continues to run until the next evaluation of the while loop condition.

switch statement for an std::pair?

I want to switch over possible values of two integers, or in another case two bools. For the sake of discussion, suppose I've done
auto mypair = std::make_pair(foo, bar);
How can I achieve the equivalent of
switch(mypair) {
case make_pair(true, false): cout << "true and false"; break;
case make_pair(false, true) cout << "false and true"; break;
case default: cout << "something else";
}
with C++11? (C++14/17 also relevant if that helps)?
You can only switch on an integral type, but if you can devise a function to map your pair (or any complex type) to an integral type, you can declare it as constexpr (C++11) to indicate it can be resolved at compile time. Then it is acceptable as a case expression.
Simple example:
enum Action { peel, eat, juice };
enum Fruit { apple, orange, banana };
constexpr unsigned int switch_pair(Action a, Fruit f) {
return (a << 16) + f;
}
Then define the switch like this:
switch(switch_pair(mypair.first,mypair.second))
{
case switch_pair(peel,apple): std::cout << "Peeling an apple" << std::endl; break;
case switch_pair(eat,apple): std::cout << "Eating an apple" << std::endl; break;
case switch_pair(juice,apple): std::cout << "Juicing an apple" << std::endl; break;
default:
throw std::runtime_error("We only have apples!");
}
C++'s switch statement doesn't have the pattern matching power of many other languages. You'll need to take a slightly different approach.
Here's a possibility I threw together:
pair_switch(my_pair,
std::make_tuple(true, false, []{ std::cout << "true and false"; }),
std::make_tuple(false, true, []{ std::cout << "false and true"; }));
You supply a std::pair<bool,bool> and a set of cases as std::tuples, where the first two elements match the pair you pass in and the third element is a function to call for that case.
The implementation has a few template tricks, but should be pretty usable:
template <typename... Ts>
void pair_switch(std::pair<bool,bool> pair, Ts&&... ts) {
//A table for the cases
std::array<std::function<void()>, 4> table {};
//Fill in the cases
(void)std::initializer_list<int> {
(table[std::get<0>(ts)*2 + std::get<1>(ts)] = std::get<2>(ts), 0)...
};
//Get the function to call out of the table
auto& func = table[pair.first*2 + pair.second];
//If there is a function there, call it
if (func) {
func();
//Otherwise, throw an exception
} else {
throw std::runtime_error("No such case");
}
}
Live Demo

Resources