I'm trying to run a console application that will allow a user to pick which type of job they would like to run on their PC and their response will translate to which functions the program runs. The way it is written right now the program will lock up and not allow anything else when the user inputs any options other than 4 which will successfully close the program.
static void Main(string[] args)
{
int userInput = 0;
DisplayMenu();
do
{
if (userInput == 1)
{
QuickClean();
}
else if (userInput == 2)
{
DeepClean();
}
else if (userInput == 3)
{
SuperClean();
}
} while (userInput != 4);
}
static public int DisplayMenu()
{
Console.WriteLine("");
Console.WriteLine();
Console.WriteLine("1. Quick Clean");
Console.WriteLine("2. Deep Clean");
Console.WriteLine("3. Super Clean (admin needed)");
Console.WriteLine("4. exit");
var result = Console.ReadLine();
return Convert.ToInt32(result);
}
static void QuickClean()
{
Console.WriteLine("quickclean");
Console.ReadLine();
}
static void DeepClean()
{
Console.WriteLine("deepclean");
Console.ReadLine();
}
static void SuperClean()
{
Console.WriteLine("superclean");
Console.ReadLine();
}
The DisplayMenu method returns what your user chooses but you don't assign this return to your usermenu local variable.
As you have written it now, you ask for input just one time and then enter the loop without setting the local variable usermenu to the user choice so it is still zero when it reaches the while to test the exit condition and the loop enters the infinite condition.
You need to move the call to DisplayMenu inside the loop and assign the return value to usermenu, so your user can see again the menu and input a different choice and you can perform the required operations.
static void Main(string[] args)
{
int userInput = 0;
do
{
userInput = DisplayMenu();
if (userInput == 1)
{
QuickClean();
}
....
} while(userInput != 4)
}
I suggest also to change the code in DisplayMenu and avoid to use Convert.ToInt32 to parse the user input. If the user doesn't type a number the Convert.ToInt32 will crash your program. Instead use Int32.TryParse
static public int DisplayMenu()
{
Console.Clear();
while(true)
{
Console.WriteLine("");
Console.WriteLine();
Console.WriteLine("1. Quick Clean");
Console.WriteLine("2. Deep Clean");
Console.WriteLine("3. Super Clean (admin needed)");
Console.WriteLine("4. exit");
int result;
if(Int32.TryParse(Console.ReadLine(), out result))
return result;
else
Console.WriteLine("Please enter a number");
}
}
You are not storing the returned value anywhere. userInput is still 0 after DisplayMenu() is called, that's why you get into an infite loop at the do-while.
do{
int userInput = DisplayMenu();
[...]
} while (userInput != 4)
Related
I am trying to make a small practice app, where user is asked their name, if its "joni" then there is a reply with YES or EXIT question. if User types YES it loops to asking question again, if user types EXIT it stops.
My problem is, how to make loop of asking YES or EXIT question if the user types different thing?
for example user types NO, so it will be asked again PLEASE TYPE YES or EXIT. But in my app it just exits if user types different thing than YES.
string? myValue;
do
{
Console.Write("Hey whats ur name?: ");
string? myName = Console.ReadLine();
if (myName == "joni")
{
Console.Write("Hey joni! Do you want to conitnue? YES or EXIT: ");
}
else
{
Console.Write("Hey student! Do you want to conitnue? YES or EXIT: ");
}
myValue = Console.ReadLine();
} while (myValue.ToLower() == "yes");
if (myValue.ToLower() == "exit")
{
Console.WriteLine("THANKS FOR USING MY APP!");
}
Console.ReadLine();
One way:
myValue = Console.ReadLine();
while (myValue.ToLower() is not "yes" and not "exit")
{
Console.WriteLine("PLEASE TYPE YES or EXIT");
myValue = Console.ReadLine();
}
I developed the menu() function to solve this problem. If the accepted entries are incorrect, the program prompts the user to enter a new menu value.
public static bool menu()
{
string? myValue;
do{
Console.WriteLine("Your Chooice: ");
myValue = Console.ReadLine();
} while (!(myValue.ToLower().Equals("yes") || myValue.ToLower().Equals("exit")));
if (myValue.ToLower() == "yes")
return true;
return false;
}
The menu() method can be used as follows:
static void Main(string[] args)
{
do{
Console.Write("Hey whats ur name?: ");
string? myName = Console.ReadLine();
Console.WriteLine("Name: {0}", myName);
} while (menu());
Console.ReadLine();
}
I am trying to create the menu for a mastermind game which can be ran in a command prompt using C#. The issue I am running into is capturing the users input for the menu. If they enter a 2 then it should display that they entered the number two and if not then it would say they have not displayed the number two.
The issue I am having is that it wont turn the users input into a working integer and will either come up saying that it can't explicitly convert from System.ConsoleKeyInfo to int or string to int.
using System;
namespace MasterMind
{
class Program
{
static void Main(string[] args)
{
Console.ForegroundColor = ConsoleColor.Green;
Console.WriteLine(" MasterMind's Main Menu");
Console.WriteLine(" 1: Play");
Console.WriteLine(" 2: Help");
Console.WriteLine(" 0: Exit");
int userinput = Console.ReadKey();
if (Nuserinput == 2);
{
Console.WriteLine("This is a number 2");
}
else
{
Console.WriteLine("This is not a number 2");
}
}
}
}
Console.ReadKey() returns a ConsoleKeyInfo object, which is not an int object. You can get a char from that, for example:
var key = Console.ReadKey();
var keyChar = key.KeyChar;
If you expect that char value to represent an integer, you can convert it to one:
int keyInt = (int)Char.GetNumericValue(keyChar);
Aside from other error checking you might want to put in place in case the user doesn't enter a valid integer, this would at least get your the integer value you're looking for.
Console.ReadKey() returns a ConsoleKeyInfo, so you'll need to do something like this:
ConsoleKeyInfo data = Console.ReadKey();
int num;
if (int.TryParse(data.KeyChar.ToString(), out num) && num == 2)
{
Console.WriteLine("This is a number 2");
}else{
Console.WriteLine("This is not a number 2");
}
Change your
int userinput = Console.ReadKey();
if (Nuserinput == 2)
To:
string userInput = Console.ReadKey().KeyChar.ToString();
if(input == "2")
Or covert the string to an int as shown in other answers. But for this, a string works fine.
My input gets checked by "TryParse". And if it is false I want to let the user retype it correctly. But when I click any key after the check it deletes everything above cause of "Console.Clear();". - I want to delete only the input part and nothing above it.
namespace Practice
{
class Program
{
static void Main(string[] args) // Main Method
{
byte age1, age2;
string input;
do
{
Console.Write("Enter Age 1: "); input = Console.ReadLine();
if (!byte.TryParse(input, out age1)) Error();
} while (!byte.TryParse(input, out age1));
do
{
Console.Write("Enter Age 2: "); input = Console.ReadLine();
if (!byte.TryParse(input, out age1)) Error();
} while (!byte.TryParse(input, out age2));
}
static void Error()
{
Console.ForegroundColor = ConsoleColor.Red;
Console.Write("Invalid Input...");
Console.ResetColor();
Console.ReadKey();
Console.Clear();
}
}
}
I'm not sure that you can erase a single line from the Console buffer. But you can simulate it if you change the second while in your code:
while (!byte.TryParse(input, out age2) && counter)
{
Error();
Console.WriteLine("Enter Age 1: {0}",age1);
Console.Write("Enter Age 2: ");
input = Console.ReadLine();
} // Check And Error Output
with this line Console.WriteLine("Enter Age 1: {0}",age1); after the Console.Clear(); executes, It seems like you have erased the wrong input line.
I have tried to create a C# program that gives the user 3 options:
Create name (gets the user to enter their first name and surname and display it as J.Blogg)
Factorial of a number (outputs as for example 5x4x3x2x1 =120 which is the factorial of 5
Quit
I have the program work fine but when I try picking option 1 (create name) and then option 2 it goes to option 1 instead and then it doesn't lets me Quit (option 3).
I'm new to programming so it could be simple but I can't see where i'm going wrong,
Any help would be very greatful.
I want to keep the same layout, I think my problem could be the loops but any help and improvement would be great.
static void Main(string[] args)
{
//The value returned from the topmenu method is stored in a variable called useroption
int useroption;
useroption = topmenu();
// excute while loop untill option is not 1-3
do
{
if (useroption == 1)
{
Console.Clear();
Createname();
//break;
}
if (useroption == 2)
{
Console.Clear();
factorial();
// break;
}
if (useroption == 3)
{
Console.Clear();
Console.WriteLine("Thank you for using my program, Good bye !!!");
// break;
}
//topmenu();
}
while (useroption != 3);
Console.ReadKey();
}
//This method present the user with an menu which the user has a choice of 3 options
static int topmenu()
{
int option;
string option_str;
Console.Clear();
Console.WriteLine("********************************************************************************");
Console.WriteLine("********************************************************************************");
Console.WriteLine("********* OPTION 1 : Enter your name *********");
Console.WriteLine("********* OPTION 2 : Enter the number you want to factorise *********");
Console.WriteLine("********* OPTION 3 : Quit *********");
Console.WriteLine("********************************************************************************");
Console.WriteLine("********************************************************************************");
option_str = Console.ReadLine();
option = Convert.ToInt32(option_str);
Console.Clear();
if (option < 0 || option > 3)
{
Console.WriteLine("You have enter an invald option,");
Console.WriteLine("Please chose a option between 1-3 (Please press any key to return to main menu)");
Console.ReadLine();
Console.Clear();
topmenu();
}
else
{
Console.WriteLine("You have chosen option: " + option + " (Please press any key continue)");
}
Console.ReadKey();
return option;
}
//this method asks user to enter their name (1st name then surname) and presents it back to the user as their intial(1st name) and surname
static void Createname()
{
string firstname, surname, firstname_str, surname_str, userfullname;
Console.Clear();
Console.WriteLine("Please enter your first name ");
firstname_str = Console.ReadLine();
firstname = Convert.ToString(firstname_str);
Console.Clear();
Console.WriteLine("Please enter your surname name ");
surname_str = Console.ReadLine();
surname = Convert.ToString(surname_str);
Console.Clear();
userfullname = firstname + surname;
Console.WriteLine("You have entered your name as " + firstname[0] + "." + surname);
Console.WriteLine("(Please press any key to return to main menu)");
Console.ReadKey();
topmenu();
}
//this method asks the user to enter a number and returns the factorial of that number
static double factorial()
{
string number_str;
double factorial = 1;
Console.WriteLine("Please enter number");
number_str = Console.ReadLine();
int num = Convert.ToInt32(number_str);
// If statement is used so when the user inputs 0, INVALID is outputed
if (num <= 0)
{
Console.WriteLine("You have enter an invald option");
Console.WriteLine("Please enter number");
number_str = Console.ReadLine();
Console.Clear();
num = Convert.ToInt32(number_str);
//Console.Clear();
//topmenu();
//number_str = Console.ReadLine();
}
if (num >= 0)
{
while (num != 0)
{
for (int i = num; i >= 1; i--)
{
factorial = factorial * i;
Console.Write(i + " * ");
}
Console.WriteLine("= "+factorial+ " which is factorial of " + number_str.ToString() );
Console.WriteLine("(please any key to return to main menu)");
Console.ReadKey();
Console.Clear();
topmenu();
}
}
return factorial;
}
}
}
Just put these line inside do...while
int useroption;
useroption = topmenu();
rearrange as following...
int useroption;
// excute while loop untill option is not 1-3
do
{
useroption = topmenu();
and your program will work fine
The full code is here : http://pastebin.com/fCh0ttUY
First of al, set useroption to 0 after executing some code. Otherwise it will keep executing it.
Second, ReadKey() right before your while statement. Otherwise you won't be able to read the input.
The issue is that although you display topmenu again you never re-assign the value of useroption.
As gypsyCoder said, moving the display of your menu inside the do{}while() block will fix your issue because it will cause the useroption to be re-assigned each time round the loop.
I'm making a program that has little programs inside of it, and I've come to a dilemma. On my first mini-program which rearranges digits to find the greatest possible number from those digits, it asks if the user wants to quit. If they respond "Yes" then the function returns 0 which is evaluated in the main(string[] args) method. My problem is that whenever the user says "No", the mini-program still doesn't continue. Here's my source:
namespace ACSL_Competition
{
class Program
{
static int DigitRearranger()
{
string[] mainString = {};
Console.WriteLine("---------Welcome to the Digit Re-arranger!---------");
Console.WriteLine("I take a positive number up to 10000, and find the highest number that can be made out of its digits.");
Console.WriteLine("Instructions: Enter a number up to 10000, and see the results!");
drLabel:
Console.Write("Your Number: ");
string input = Console.ReadLine();
int inputNumber = 0;
try { inputNumber = int.Parse(input); }
catch (Exception ex) { Console.WriteLine("Error: {0}", ex.Message); goto drLabel; }
/*Placeholder code for the moment*/Console.WriteLine(inputNumber.ToString());
evaluate:
Console.Write("Do you want to exit? Yes/No: ");
if (Console.ReadLine().Equals("Yes"))
return 1;
else if (Console.ReadLine().Equals("No"))
{
goto drLabel;
}
else
{
return 1;
}
}
static void Main(string[] args)
{
Console.WriteLine("Welcome to the ACSL Competition Program. Choose a program to begin:");
Console.Write("\n\t");
Console.WriteLine("1\tDigit Re-arranger");
label:
Console.Write("\nProgram: ");
string input = Console.ReadLine();
int number = 0;
try { number = int.Parse(input); }
catch (Exception ex) { Console.WriteLine("Error: {0}", ex.Message); goto label; }
if (number == 1)
{
Console.WriteLine("\n");
if (DigitRearranger() == 1)
{
goto label;
}
else if (DigitRearranger() != 1)
{
DigitRearranger();
}
}
else if (!number.Equals(1))
{
Console.WriteLine("Not a valid program.");
goto label;
}
//----------------
Console.ReadLine();
}
}
}
The underlying problem is that you're calling readline twice. The first time it gets the entered value, i.e. Yes, the second time you call it there is no data to read so it returns "". If you need to reuse the same input store it in a variable, i.e.
string inputVal = Console.ReadLine();
I hate goto statements, maybe you could restructure your code in to a while loop, something like:
bool exit = false;
while(!exit)
{
Console.Write("Your Number: ");
//Your main code
Console.Write("Do you want to exit? Yes/No: ");
if(Console.ReadLine() != "No")
exit = true;
}
In fact, you could get rid of the exit variable, just do while(true) and return if the user enters anything other than no.
I have a few suggestions:
Write your code to be more modular to improve readability. The Main() method should only drive the outer UI loop, each module provides its own UI.
Never use goto statements.
Don't use Console.Readline() inside an if condition (when not "Yes", it was called twice).
Here is my refactored version of your code:
class Program {
static void DigitRearranger()
{
string response = "";
int num;
do
{
Console.Clear();
Console.ForegroundColor = ConsoleColor.Yellow;
Console.WriteLine("---------Welcome to the Digit Re-arranger!---------");
Console.WriteLine("I take a positive number up to 10000, and find the highest number that can be made out of its digits.");
Console.WriteLine("Instructions: Enter a number up to 10000, and see the results!");
Console.ResetColor();
Console.Write("Your Number: ");
if (!int.TryParse(Console.ReadLine(), out num))
{
Console.WriteLine("Not a number. Press any key to continue");
Console.ReadKey();
continue;
}
//todo: reaarrange the number & print results
/*Placeholder code for the moment*/
Console.WriteLine(num);
Console.Write("Do you want to exit? Yes/No: ");
response = Console.ReadLine();
} while (response.ToLower() != "yes");
}
//UI driver only in Main method:
static void Main(){
string response = "";
do
{
Console.Clear();
Console.WriteLine("Welcome to the ACSL Competition Program. Choose a program to begin:");
Console.WriteLine("\n\t1\tDigit Re-arranger");
Console.WriteLine("\tq\tQuit");
Console.Write("\nProgram: ");
response = Console.ReadLine();
switch(response)
{
case "1":
DigitRearranger();
break;
case "q":
break;
default:
Console.WriteLine("Not a valid program. Press any key to continue");
Console.ReadKey();
break;
}
} while (response.ToLower() != "q");
Console.ReadLine();
}}