Fonction rejouer en c# [duplicate] - c#

This question already has answers here:
Option yes/no C# Console
(7 answers)
Closed 3 years ago.
I am learning about C # programming and I stumble on a part of my code. I use visual studio 2017.
I develop a mystery number game and I would like to make sure to replay but I do not know how to do it.
I would like that when we press O or N it plays again or else it quits, but I can not. Scanf and printf do not work. Thank you for your next answer.
char play;
bool isvalid = true;
void Number()
{
//Code...
While(isvalid);
{
Console.WriteLine("want to play again o/n ");
if(play == 'o')
{
Number();
}
else
{
play == 'n';
}
}
}
Number();

I see couple of issues in the pasted code:
First of all, you there is a semicolon after the while loop. Because of it, the lines in the curly brackets are not getting executed again and again as you expect them to.
Second - you are not populating play variable. You should use Console.Readline (you can enter any string and then hit enter to come out of input prompt) OR Console.Read (to read just 1 char)
Third - You are calling Number function again and again - if you play your game for sufficiently long time it would cause stack overflow exception.
What I understood from your code is you want to execute some code again and again if user keeps on entering 'o' character. Otherwise you want to stop that loop.
The code would be :
void Number()
{
//Code...
While(isvalid);
{
Console.WriteLine("want to play again o/n ");
play = Console.Read();
if(!string.IsNullOrEmpty(play) && play.Equals('o', CultureInfo.InvariantCulture)
{
/////// Some code you want to execute;
}
else
{
////// Some code you want to execute if user enters anything other than 'o'.
////// If you want to stop loop, set isValid = false; OR use break statement
}
}
}
I know that this answer may not solve your problem completely.
Hope this helps you to understand what code you should write.

Related

C# How do I make my loop not loop back to the first line?

I have been working on a text adventure for a while, but I am having an issue. I have a tutorial, but I want to know how when the user types something that isn't listed, instead of asking the question again, just displaying the option. My example here is a tutorial option that isn't available yet, so they have to type back. I want it so if they type anything other then back, it just displays [Back] and not "That option isn't listed.". In the code example I have tried to use more than one static void because maybe I couldn't reference my own void but that wouldn't work, And I separated the writing and the back option into two but it still doesn't work. When the code example has SW(60, "text") that is just a custom thing for slow write and the 60 is 60 millisecond delay. So, whenever I run it, and type something other then back it will say "That option isn't listed.", like planed but then somehow clear the line and tell you the settings are disabled.
Here is my code.
'''
static string TutorialBack;
public static void TutorialLine()
{
Console.Clear();
SW(40, "The tutorial is currently being devolped, thank you for your patience and support.");
Game.TutorialOof();
}
public static void TutorialOof()
{
Game.Tutorial();
}
static void Tutorial()
{
Thread.Sleep(1600);
Console.WriteLine();
SW(40, "[Back]");
Console.WriteLine();
TutorialBack = Console.ReadLine();
if (string.Equals(TutorialBack, "back", StringComparison.CurrentCultureIgnoreCase))
{
Console.Clear();
Game.Menue();
}
else
{
SW(60, "That option isn't listed.");
Game.TutorialOof();
}
Thanks for any help.
Text adventures are still alive? ;)
I think you should use the var to check equals not the type (string).
// ...
if (TutorialBack.Equals("Back", StringComparison.CurrentCultureIgnoreCase))
{
Console.Clear();
Game.Menue();
}
// ...
Edit: Sorry if I misunderstood what you mean. If you want keep the current just quote out the instruction inside else.
else
{
//SW(60, "That option isn't listed.");
//Game.TutorialOof();
}
Or
else
{
//SW(60, "That option isn't listed.");
Game.TutorialOof();
}

Execute specific blocks of code based on which key on the keyboard is pressed

I am very new to the programming world and recently dove into c#. I don't want to waste your time so I'll get right to it. I wanted to create a program just to test my knowledge, and thought I could attempt to execute specific blocks of code based on which key on the keyboard is pressed by the user. I tried doing this by creating an event handler that contained if statements, but then realized I didn't know how to have the event handler active in the program.
For example, and as you can see in the below snippet, after the WriteLine in Line 5 lets say I wanted to raise the EventKeyPress event so that it waits for user input and reads the key they have pressed and reacts accordingly, how would I do that?
Again, I'm almost a complete beginner and have searched around for explanations about event handlers for hours and still can't wrap my head around what I am supposed to do or if I am even using the event handler correctly. Thanks in advance!
static void Main();
{
if (search == "Ball")
{
Console.WriteLine("Press enter to exit or backspace to return to the search bar")
// RIGHT HERE
}
else
{
Console.WriteLine("Sorry, I don't recognize {0}", search);
}
void EventKeyPress(object sender, KeyPressEventArgs e)
{
for (int i = 0; i < 1;)
{
if (e.KeyChar == (char)Keys.Enter)
{
// exit app
}
else if (e.KeyChar == (char)Keys.Back)
{
// go back to search
}
else
{
i = 0; // error
}
}
}
}
So, you're asking for something that involves Threading which is not a beginner thing to accomplish at all. The best way to do this for a beginner is to ask for a prompt, then accept as an input. For example.
Console.WriteLine("Hello, what's your name?");
string nameStr = Console.ReadLine();
Console.WriteLine($"Hello, {nameStr}");
You can then use your variable and apply it to an if/while or whatever kind of conditional.
if (nameStr == "Matt"){
//Do This Code.
}
Once you have that code, add a sequential method that will ask the user to return to the main menu or whatever you want it to do.
Main.ReturnMenu(); //Or whatever you want to use.

Process is terminated due to StackOverflowExeption - C#

I have this problem with my code I cant fix.
I am making a quiz, but the questions mustnt be asked twice so I avoided that, but when it runs out of options it crashes.
It also could be the code after it, but I dont think so.
Here is my code:
private static void chooseQuestion()
{
Random randomQuestion = new Random();
int returnValue = randomQuestion.Next(1, 3);
switch (returnValue)
{
case 1:
if (randomValues.questionOneChosen != 1)
{
questionOne();
}else
{
chooseQuestion();
}
break;
case 2:
if (randomValues.questionTwoChosen != 1)
{
questionTwo();
}else
{
chooseQuestion();
}
break;
}
endQuiz();
}
and here is what is after it:
private static void endQuiz()
{
Console.Clear();
Console.WriteLine();
text.centered("You completed the QUIZ, well done!");
Console.WriteLine();
text.centeredWrite("Press ENTER to go back to the menu");
string input = Console.ReadLine();
if (input == "")
{
Menu.main();
}else
{
endQuiz();
}
}
If you need more code to help me, please ask me.
Thanks in advance!
A StackOverflowException on StackOverflow, nice!
Does Menu.main() end up calling chooseQuestion()?
When a function is called, a new entry on the stack is created with room for all its local variables and the address to return to when it returns. If a function calls itself (recursive call), its original stack entry is not released. If it calls itself often enough without returning, the stack will eventually run out of room and give this exception. Having said that, the stack is pretty big - I think the default is 1 megabyte - so you need a lot of recursive calls to exhaust it.
You've got two functions which both call themselves. If they do it often enough, you'll run out of stack space. Just replace the recursive calls with a loop. Here's your first function:
private static void chooseQuestion()
{
bool endQuizChosen = false;
while ( !endQuizChosen ) {
Random randomQuestion = new Random();
int returnValue = randomQuestion.Next(1, 3);
// ... the rest of the function ...
endQuizChosen = endQuiz();
}
}
and edit endQuiz() to not call itself but to return true if user wants to stop and false if they want to go on.
Your chooseQuestion method's logic goes like this:
a. Pick a 1 or 2, randomly
b. If 1, and I haven't asked question 1 yet, show question 1
c. if 1, and I have asked question 1, go to step (a)
d. repeat (b) and (c) for question 2
...
once you answer both questions, you try to get another random question. But there are no more questions available. So you recurse into an exception.
Don't write your logic this way. Use a collection, and remove the item from the collection after you've shown that question. When the collection is empty, you're done.
This is never getting set.
randomValues.questionOneChosen
So whatever it is, if it's not 1 or 2 the method is going to call itself again. It's probably always zero.

IF condition is not satisfied, return on the beginning and don't do anything [closed]

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 7 years ago.
Improve this question
I have a pretty big code so I wont put it here...
I made some calculation which works and now I want to repair certain things.
I created for loop with statement: if (my condition) is true break and
save, else if (condition is not true) show message box and report what
is wrong (like example input is 0 and should not be 0). But after that
my calculation goes on till the end and dont stop there. How to stop
it there until my condition is not satisfied?
What to add with return?? I have it in private void function on
button click.. This bothers me becouse in my program there is lots of
if conditions with show/hide options. So when program continue with
calculation it show lots of 0 and bad numbers..
I am calling this function (radio button checked) with another one (button click)
The input inside if statement is from textboxes converted to numbers
if (Math.Abs(miSdCrtica - _dMiSd) < 0.01)
{
epsilonS1 = epsilonS1Pretpostavka;
zeta = zetaRacunska;
ksi = ksiRacunski;
xNeutralnaOs = ksi * _dd;
zKrakSila = zeta * _dd;
racunskiAs1 = (_dMed * 1000) / (zeta * _dd * dFyd);
break;
}
else if (_dMiSd < 0.086)
{
MessageBox.Show("Error - check input");
return;
}
And after this Error - check input thing, code continues and give me bunch of zero's (0)
I hope this helped to clear up some things
Problem demo
I have some texboxes for UI, radio button to choose from 2 conditions and button for calculation
radiobutton
private void combobox_indexChanged ()
if statement (radiobutton checked)
for loop (written above)
if statement (written above)
else if statement (written above)
button click
private void button clicked()
calls radiobutton checked (do calculation)
hide/show bunch of labels (their results are 0 with else if statement from above)
how to stop it so when MessageBox.Show("Error - check input"); is shown, the button click function does not continue to hide/show labels but to stop until UI is right?
I hope now is clear what i want to do
Just use "return;" to exit out of the void method wherever you want to stop the execution.
From the description, I suppose your button click event looks something like:
void Button1_Click(...){
if(radioButton1.Checked){
RadioButton1Checked();
}
if(radioButton2.Checked){
SomeOtherFunction();
}
...
}
void RadioButton1Checked(){
for(...){
//code from the question
}
}
You don't want the other code to run if code in RadioButton1Checked "failed". So you could change that function to return bool.
bool RadioButton1Checked(){
for(...){
if (Math.Abs(miSdCrtica - _dMiSd) < 0.01)
{
//...
racunskiAs1 = (_dMed * 1000) / (zeta * _dd * dFyd);
break;
}
else if (_dMiSd < 0.086)
{
return false;
}
}
return true;
}
void Button1_Click(...){
if(radioButton1.Checked){
if(!RadioButton1Checked()){ //if the function returns false
//Display message box
return;
}
}
if(radioButton2.Checked){
if(!SomeOtherFunction()){
//Display message box
return;
}
}
...
}
Alternatively, you could throw an ArgumentException from your function and catch it.
else if (_dMiSd < 0.086)
{
//I suggest you to specify which input exactly is faulty
throw new ArgumentException("Error - check input");
}
void Button1_Click(...){
try{
if(radioButton1.Checked){
RadioButton1Checked();
}
if(radioButton2.Checked){
SomeOtherFunction();
}
...
}catch(ArgumentException e){
MessageBox.Show(e.Message);
}
}
A general suggestion is that you make all your calculation functions parametric. A function should take a set of parameters and calculate a result based on those parameters only (without variables declared outside the function scope - i.e class members or global variables).
I suppose you have something like:
class ...{
double epsilonS1;
double zeta;
void Button_Click(..){
double.Parse(textBoxEpsilon.Text, out epsilonSi);
zeta = 0.02;
Calculate();
}
void Calculate(){
epsilonS1 = epstilonS1 * zeta * 0.01f;
}
}
Problem with this is if your calculation process needs to fail - then you had already changed a lot of your 'global' variables, and it's not easy to return to the previous state (before you called the function).
Instead of that, try to make your functions like so:
class ...{
void Button_Click(..){
double epsilon = 0;
double.Parse(textBoxEpsilon.Text, out epsilon);
double result = Calculate(epsilon, zeta);
}
//function takes parameters, and returns a result.
//It neither reads nor changes variables that are outside its scope
double Calculate(double epsilonS1, double zeta){
return epsilonS1 * zeta * 0.01f;
}
}
If function written like this fails, you can be sure that it didn't change any global variables, so the program 'state' is the same as it was before the function was called.
Yes, it's a long answer, a lot needed to be said (and assumed since I didn't actually see your code).
P.S.
RadioButton.Checked values are good parameters for a function (those that are relevant to the calculation - those that are only used to indicate whether UI should display a value or not should be left outside). Instead of calling (what I assume you are doing) a lot of individual functions based on checkbox values, you could just pass those values to the function and make calculations (or call other functions) based on them.
void Calculate(double epsilon, double zeta, bool calculatePhi, bool showZulu){
epsilon = zeta * 0.01;
if(calculatePhi){
phi = epsilon / 2;
if(phi < 0.1)
throw new ArgumentException("Invalid input - epsilon");
}
}
If you need to return multiple values from a function, a simple way to do that is to create a class that will contain those values, then return an instance of that class.
class Result{
public double Epsilon {get; set;}
public double Zeta {get;set;}
...
public bool DisplayZeta {get;set;}
}
And your calculate function could look like:
Result Calculate(double epsilon, double zeta, bool calculatePhi, bool showZulu){
Result result = new Result();
result.Epsilon = zeta * 0.01;
if(showZulu){
result.DisplayZeta = true;
}
return Result;
}
By the way, when you need to do calculations, don't put them in the event handlers, make specialized functions (methods) that perform them. Instead of doing your calculation in the RadioButton_Checked(...) event, do it in Calculate() method, which you can call from the event handler and the button click.
Why don't you throw a breakpoint on the line break;? It might help to see what's going on with your numbers, and also to make sure you are passing in the right values.
When Visual Studio stops at the breakpoint, mouse over all of your variables in your code and make sure they make sense.
If you find something that doesn't look right, you're one step closer to identifying the problem.

Using Timer and colour to display morse code

Hi Guys i'm trying to let my Screen blink a morse code out using timer , but no luck, can you spot any problem?
Sry but i feel sad for those who cant think out of the box and just mark a -2 without even understanding the situation.
Anyway, found about using await Task.Delay(100) but gridHalfFront.Opacity = 1; isnt being "activated" when its being read. not sure why.
async public void RunMorseCode()
{
foreach (char c in word.ToCharArray())
{
string rslt = Codes[c.ToString()].Trim();
foreach (char c2 in rslt.ToCharArray())
{
if (c2 == '.')
{
gridHalfFront.Opacity = 0;
await Task.Delay(100);
}
else
{
gridHalfFront.Opacity = 0;
await Task.Delay(1000);
}
gridHalfFront.Opacity = 1;
}
}
}
use System.Threading.Thread.Sleep(1000) and/or System.Threading.Thread.Sleep(3000) inside yr loop to make yr screen blink on and off
gridHalfFront.Opacity = 1;
if (c2 == '.')
{
System.Threading.Thread.Sleep(1000);
}
else
{
System.Threading.Thread.Sleep(3000);
}
gridHalfFront.Opacity = 0;
change it to the way it best for you, but dont use those timers
Your code is missing the Timer event handler. After calling Start() and after the elapsed time a Tick event from the Timer will be raised. There you have to change the opacity.
I think you are misunderstanding the use of a Timer. If you put the following code at the top of StartTimer you will see what I mean.
Console.WriteLine("Started {0}", inputTiming);
When you run you will get a bunch of timers are being created immediately. This is not what you want for two reasons. Firstly, they are all assigned to the same variable, so the second is 'logically' killing off the first, etc. Secondly, you don't want them created all at once, as all of the 1 second ones will all run at the same time after 1 second, and all of the 3 second ones will run together after 3 seconds. And, as already mentioned, to run code after the timer expires you need to hook up the event.
BIG EDITS Sorry didn't realise you were looking at Metro. What I have said above still holds, but I will back away from providing a solution.
Given the comments about Sleep() not working on Metro, I think you need to so all the code inside the timer for one character, and then set the interval for the next character from within the timer. Will provide some code in a few minutes...

Categories