Or "||" syntax clarification - c#

In C#, if I want to check to make sure that a value does not equal X or Y, I would write something like this:
if(x != 1 && x != 2)
{
//dosomething
}
I want to see if there is a way to write that with OR instead of AND. Something like this (which doesn't work, but its what I am trying to do):
if(x != (1 || 2))
{
//dosomething
}
Obviously that doesn't work because it is trying to evaluate 1 || 2 as its own statement. Does there exist a way to write that correctly?

You can always invert an AND into an OR:
if (!(x == 1 || x == 2))
{
...
}
You have to reverse all the conditions to do it though, as above. The process for doing so is described in De Morgan's Laws (thanks #RichardEverett!).

You could try this one:
if(!(x == 1 || x == 2))
but honestly, I don't see the reason of doing so.
This statement if(x != 1 && x != 2) is far more clear and readable than the above and it does the same.
This (x == 1 || x == 2) evaluates to true if x is either 1 or 2. Hence taking the negation of this, you get that you want.

No, C# doesn't support such a construct presently.
The following is about as close as I could get it, but it's slow!
if (!new[] { 1, 2 }.Contains(x)) { ... }

Related

Understanding IF Logic in my code

I thought I understood programming well enough to get the results I was looking for but alas this simply is not working for me. I've reduced my code to a simple Console application for assistance. The goal was to print out a 5x5 grid of 1's and 0's. Actually, I wanted to create a random x and y value such as 2 and 1 and I call this EmptyX and EmptyY. In this spot and only this spot, I should get a '0' printed. In all other cells there should be '1'. So it should be a grid of all 1's expect for the spot identified by EmptyX and EmptyY. My code below, although works, puts zero's down the entire column and row.
Why is this happening? I keep looking at my code and it seems my logic is good to me but of course it is not. How else can I make the grid with only a single 0 at the spot EmptyX and EmptyY?
class Program
{
static void Main(string[] args)
{
int EmptyX = new Random().Next(5);
int EmptyY = new Random().Next(5);
for (int y = 0; y < 5; y++)
{
for (int x = 0; x < 5; x++)
{
if ((x != EmptyX) && (y != EmptyY))
Console.Write("1");
else
Console.Write("0");
}
Console.WriteLine();
}
Console.ReadKey();
}
}
Something like this with the 2 and 1 example:
11111
11011
11111
11111
11111
The problem is you have confused AND and OR in the context of NOT. This is a very common logic error (as seen in this post).
If conditions, believe it or not, can mess up even experienced developers. I have seen it happen (never intentionally) over and over to senior developers who aren't paying attention. So, be reassured, you are not alone.
The best way to deal with complicated if conditions is to write Ridiculously Obvious Code (ROC) where you make the point of the logic ridiculously clear by using obvious naming and maybe being a bit verbose with the code. In most cases, drawing out the code a bit doesn't affect performance, because the compiler will optimize out the extra working variables and generate exactly the same IL.
So for example, instead of writing
if ((x != EmptyX) || (y != EmptyY)) //I fixed it for you
Console.Write("1");
else
Console.Write("0");
You could write something like
bool isOnEmptyColumn = (x == EmptyX);
bool isOnEmptyRow = (y == EmptyY);
bool isOnEmptyCell = isOnEmptyColumn && isOnEmptyRow;
if (isOnEmptyCell)
{
Console.Write("0");
}
else
{
Console.Write("1");
}
The above takes several lines more of code but is ridiculously obvious, and makes it much harder to goof up the combination of your logical operators.
If you find that the verbosity of the logic check makes your method too long, you can extract the logic to a separate function. In this example, I also use guard pattern to simplify the logic even further:
private bool IsOnEmptyCell(int x, int y)
{
if (x != EmptyX) return false;
if (y != EmptyY) return false;
return true;
}
//Main program
if (IsOnEmptyCell(x,y))
{
Console.Write("0");
}
else
{
Console.Write("1");
}
Again, rest assured this won't affect performance, as the compiler will automatically inline your code when necessary. The important thing is to focus on writing source code that is easy to understand and difficult to misunderstand.
your code will print 0 whenever
x=EmptyX or y=EmptyY
for example
if EmptyX =3 and EmptyY=3 and x=0 and y=3
if ((x != EmptyX) && (y != EmptyY))
if ((x != 3) && (y != 3))
if ((0 != 3) && (3 != 3))
if ((true) && (false))
if (false)
and it will not print '1' when it should.
change your condition to
if ((x != EmptyX) || (y != EmptyY))
Modify your if else condition.
Method-1.
if ((x == EmptyX) && (y == EmptyY))
Console.Write("0");
else
Console.Write("1");
Method-2.
if ((x != EmptyX) || (y != EmptyY))
System.out.print("1");
else
System.out.print("0");

How can find record with odd id in database by lambda expression?

I want to know is there any way to find record with odd id in Database by using lambda expression in c#?
I try it but it is not working !!
GoogleEntities db = new GoogleEntities();
List<tbl_search> _oddSearchList = db.tbl_search.Where(c => (c.id / 2) == 0).tolist();
How can do it?
I think you need this
c => (c.id % 2) == 0 // modulus operator instead of divide operator.
But again, this would return an even, because ID fully divided by 2 is even. You need this
c => (c.id % 2) != 0
To get the odd number.
So, after this, your code would be this one
List<tbl_search> _oddSearchList = db.tbl_search.Where(
c => (c.id % 2) != 0
).tolist();
Use the module operator %, which checks for the rest of a division.
List<tbl_search> _oddSearchList = db.tbl_search.Where(c => (c.id % 2) == 1).tolist();
Also check if the result is 1 instead of 0. If the rest is 0, then the id is divisible by 2 and therefor EVEN.

!= operator not working as it should

I am currently trying to get my snake console game running but I have came up with something that I do not quite understand. I don't really think that the != operator is not working correctly, so I must have made a mistake but I have no idea why it it is like that:
// not working
if (food.x != snakeElements.Last().x && food.y != snakeElements.Last().y)
// working
if (!(food.x == snakeElements.Last().x && food.y == snakeElements.Last().y))
Isn't it all the same?
Using De Morgan's laws (!a && !b) is the same as !(a || b) so your first example should be:
if (food.x != snakeElements.Last().x || food.y != snakeElements.Last().y)
The && should be || in the first if.
if (food.x != snakeElements.Last().x || food.y != snakeElements.Last().y)
If you write out what you actually mean by your boolean condition, you can see more clearly what the difference is.
// not working
if (food.x != snakeElements.Last().x && food.y != snakeElements.Last().y)
This means:
"The food is not in the same column as the last snake element, and the food is not in the same row as the last snake element"
The logic error is a bit more obvious now. What if the food's position is (10,3), and the last element's position is (14,3)?
Compare with:
// working
if (!(food.x == snakeElements.Last().x && food.y == snakeElements.Last().y))
Which means:
"It's not true that (the food is in the same row as the last snake element and the food is in the same column as the last snake element)"
Now the condition is false if and only if the food has the same X and Y as the last snake element.
No, it is not same.
If this works...
if (!(food.x == snakeElements.Last().x && food.y == snakeElements.Last().y)) // working
Then this should work too...
if (food.x != snakeElements.Last().x || food.y != snakeElements.Last().y) // should work
Notice the change in the sign from logical AND (&&) to logical OR (||).
I think the boolean logic is different in two cases:
both comparisons must be not equal for the if to evaluate to true.
either one has to be not equal for if to evaluate to true
They are different.
To be clear, I'll call food.x as X and snakeElements.Last().x as X', others as Y and Y'.
First one is saying:
if X is different than X' AND Y is different than Y' is true
Second one is saying:
if X is equal to X' AND Y is equal to Y' is false
Assume that X, X', Y, Y' are integers
If we say that X = 3, X' = 5, Y = 1, Y' = 4, first statement is true, because X != X' Y != Y' are both true. However, second would also be true becase X is not equal to X'.

Beginner c# trouble

Im new to c# and Im having a little problem. I want to make an easy program to ask the user for a integer number between 1-50, and then to display on the console if its a odd number or not. So, what i tried is this:
Console.WriteLine("Skriv ut ett heltal: ");
int x = int.Parse(Console.ReadLine());
if (x == 1,3,5,7,9,11,13,15,17,19)
{
Console.WriteLine("The number is odd");
}
else
{
Console.WriteLine("The number is not odd");
}
Now i get an error at my if statements condition. How can i fix this?
C# does not allow you specify multiple values to check a variable against using a single if statement. You would need to check each value (1, 3, 5, etc) individually if you wanted to do it this way, and that would be a lot of redundant typing.
In this particular example, an easier way to check if something is odd or even is to check the remainder after dividing by 2, using the modulus operator %:
if (x % 2 == 1)
{
Console.WriteLine("The number is odd");
}
else
{
Console.WriteLine("The number is even");
}
However, if you really do need to check against a list, then the easy way is to use the Contains method on an array (an ICollection<T>, really). To make it nice and easy, you could even write an extension function that lets you check against a list in a syntactically pretty fashion:
public static class ExtensionFunctions
{
public static bool In<T>(this T v, params T[] vals)
{
return vals.Contains(v);
}
}
Then you could say:
if (x.In(1,3,5,7,9,11,13,15,17,19))
{
Console.WriteLine("The number is definitely odd and in range 1..19");
}
else
{
Console.WriteLine("The number is even, or is not in the range 1..19");
}
Voila! :)
if(x % 2 == 0)
{
// It's even
}
else
{
// It's odd
}
If you want to test whether x is a number in a particular list:
int[] list = new int[]{ 1,3,5,7,9,11,13,15,17,19};
if(list.Contains(x))
The common way to check to see if an integer is odd is to check if it divides evenly by 2:
if(x % 2 == 1)
x == 1,3,5,7,9,11,13,15,17,19 is not valid syntax for expressing multiple options. If you really want to do this then you can use a switch statement:
switch(x) {
case 1:
case 3:
case 5:
case 7:
case 9:
case 11:
case 13:
case 15:
case 17:
case 19:
// is odd
break;
default:
// is even
break;
}
The correct way would be to use the modulo operator % to determine if a number is exactly divisible by 2 or not, rather than trying every odd number, like so:
if( x % 2 == 0 ) {
// even number
} else {
// odd number
}
That's not valid C#. You can't test set inclusion like that. In any case, it's not practical to test for all the numbers in the world.
Why don't you just do this instead;
if (x &1 == 1) // mask the 1 bit
Bitwise operations are pretty quick so that code should be pretty fast.
Your if statement should be like this if you are having multiple conditions:
if any 1 of conditions is true:
if(x == 1 || x == 3 || x == 5)
{
//it is true
}
if all of the condition must be true:
if(x == 1 && y == 3 && z == 5)
{
//it is true
}
But if you are only looking for odd/even numbers. Use the % operator as the other answer says.
While, as others have pointed out, this is not the best way to solve this problem, the reason you're getting an error in this case is because you can't have multiple values like that in an if statement. You have to word it like this:
if (x == 1 || x == 3 || x == 5)
If you don't know, || is the symbol for 'or'
Try the following:
Console.WriteLine("Skriv ut ett heltal: ");
int x = int.Parse(Console.ReadLine());
Console.WriteLine(x % 2 == 1 ? "The number is odd" : "The number is not odd");
x % 2 == 1 does a modulus of 2 on the input (takes as many '2's off as possible until the number is between 0 and 2 - so 0 or 1 in this case)
One way to do that is:
if (x == 1 || 3 || 5){
Console.writeLine("oddetall");
}
or so it is possible to create an Array []
int[] odd = new int[3]; // how many odd to be tested
if(x=odd){
Console.WriteLine("Oddetall");
}

C#-Is there a way to get a do-while to accept OR statements?

I'm teaching myself some C# and got the idea to build a temperature calculator. I want to use a do-while loop to ensure the user picks a valid menu choice. What I tried to do was:
do
{
//etc etc etc;
} (while menuChoice != 1||2||3);
In other words, keep doing what is inside the loop unless menuChoice is 1, 2 or 3. VS2010 Express tells me I can't do that. Is there a way to do this that way or do I have to do something else? Any suggestions on how to do this or should I use some other solution?
do { // stuff
} while (menuChoice != 1 && menuChoice != 2 && menuChoice != 3);
do {
// etc.
} while(menuChoice != 1 &&
menuChoice != 2 &&
menuChoice != 3
);
Each of the clauses of a conjunction must be an expression that evaluates to a bool. Note that != 2 is not an expression that evaluates to a bool. In fact, it's not even a legal expression. This is why you must specify menuChoice != 2.
Also, note that you should use && because the clauses. You want menuChoice to equal 1, or to equal 2, or to equal 3. Therefore you want
!(menuChoice == 1 || menuChoice == 2 || menuChoice == 3)
as the condition in the while loop. By DeMorgan's Laws, this is equivalent to
menuChoice != 1 && menuChoice != 2 && menuChoice != 3
EDIT:
How about this? this would allow you to have a non-contiguous set of numbers and is far more extensible than having a million || statements...:
int[] menuOptions = { 1, 2, 3 };
...
while(!menuOptions.Contains(menuChoice))
Or:
do {
// etc.
} while(menuChoice > 3 || menuChoice < 1);
Just to provide yet one more solution:
using System.Collections.Generic; // for the List<T>
do
{
}
while (!(new List<Int32>(new[]{ 1, 2, 3 })).Contains(menuChoice));
And yes, this is not the best solution, it is, however, an alternative (and useful if your list of options grows).

Categories

Resources