And Operation between lists of Enums - c#

I have two lists of Enums and I want to perform And kind of operation between them. Let suppose my enum definition has 3 elements true, false and NA.
public enum myEnum {
True,
False,
NA
}
I have two lists List1 and List2 and both contain 10 elements. I want these results:
True && False = False
True && NA = NA
False && NA = False
True && True = True
False && False = False
NA && NA = NA
I want to know to that is there any built-in functionality in C# which can give me results which I mentioned above. I am trying to avoid writinig long code.

Start out writing the method that can perform the And operation that you want on just two values, using the logic that you described. This is actually handled quite easily, as if either value is False you return False, if none is False and one is NA you return NA, and if both are true you return true, the only remaining case.
public static myEnum And(this myEnum first, myEnum second)
{
if (first == myEnum.False || second == myEnum.False)
return myEnum.False;
if (first == myEnum.NA || second == myEnum.NA)
return myEnum.NA;
return myEnum.True;
}
Next, it appears that you want to compare the item from each list that is at the same index, so the first is compared to the first, the second to the second, etc., to create a new list of the same size as the other two. You can use Zip, to perform this logical operation using the method we've already defined:
var query = list1.Zip(list2, (a,b) => a.And(b));

A bool? (Nullable<bool>) has three values and gives you all of the values you expect if you use the logical and (&) operator:
(bool?)true & (bool?)false = false
(bool?)true & (bool?)null = null
(bool?)false & (bool?)null = false
(bool?)true & (bool?)true = true
(bool?)false & (bool?)false = false
(bool?)null & (bool?)null = null

Related

Is there a way to compress a check that returns a nullable boolean this into 1-2 lines?

I'm making a simple C# console app and the user has to input either a 1 or a 2 to select their option, and obviously since the user can enter absolutely anything, I need to make a check that returns their input and if it isn't a 1 or a 2, it'll return null.
This is what I made
bool? getResponse = null;
if (read == "1")
{
getResponse = true;
}
else if (read == "2")
{
getResponse = false;
}
else
{
getResponse = null;
}
Knowing C#, there's definitely a way to simplify this but I cant seem to find a way to online. Any pointers?
Probably you are looking for conditional operator ?:.
But this could be complex to maintain and difficult to read if the logic is getting complex (adding logic for read == "3" and etc.).
getResponse = read == "1"
? true
: read == "2"
? false
: null;
Another approach you can apply is switch expression for C# 9.
getResponse = read switch
{
"1" => true,
"2" => false,
_ => null,
};
The third approach is you work around with Dictionary.
using System.Collections.Generic;
using System.Linq;
Dictionary<string, bool> resultDict = new Dictionary<string, bool>
{
{ "1", true },
{ "2", false }
};
getResponse = resultDict.TryGetValue(read, out bool _result)
? _result
: null;
You can use ternary operator in a such situations like this
string read = Console.ReadLine();
bool? response = read == "1" ? true
: read == "2" ? false : null;
but it's best when there is only 2 possible ways, as u can see it's getting out of hand easily. In this situation my code above is ok, but if you have like 10 possibilities maybe something like this is a good approach
// lets say there is ways
// 1 = true, 2 = false, 3 = null
// and any other input means exception
string read = Console.ReadLine()!;
Dictionary<string, bool?> keyValues = new();
keyValues.Add("1", true);
keyValues.Add("2", false);
keyValues.Add("3", null);
bool? response = keyValues.ContainsKey(read) ? keyValues[read]
: throw new Exception();
the exception here is just for example,
my point is that when you have multiple possibilities
doing such thing with dictionary seems much cleaner than if/else, switch/case or multiconditional ternery operator
I consider this pretty unreadable, but it avoids the nested ternary.
getResponse = int.TryParse(read, out var i) && i > 0 && i < 3 ? (bool)(2-i) : null;
Parse the string into an int, make sure it is the valid range, and then do some math so you can cast it to a bool. When casting an integer type to a bool, 0 means false, and non-zero means true.

Can i have more conditions in one while-loop?

can i ask you if I can have two conditions in one while loop like this?
For example:
I've tried almost everything in my own code.
int a = 0;
bool b = false;
while(a!=5 || b!=true) {
a++;
}
Console.WriteLine("A is successfuly loaded into 5.");
Console.WriteLine("Bool is still " + b);
I expect the output to be 5, but in my program i have an infinite loop.
The variable b is set to false and does not change.
So, the condition of b!=true is always true.
This condition is on the right side of the "or" ( || ) operator.
Hence, the infinite loop results.
This is an infinite loop because of your second condition.
while(a!=5 || b!=true) uses the || (OR) operators which means as long as one of the conditions is true, the whole condition is true
T || F = T ---> True OR False == True
F || T = T ---> False OR True == True
T || T = T ---> True OR True == True
F || F = F ---> False OR False == False
You assigned b = false and then check for b!=true(equivalent to b == false [which is what you assigned it]). This condition is true and because of which it infinitely enters the loop.
Both a!=5 || b!=true have to be false for it to exit the loop.
When designing a check with multiple conditions, the key is to think about how the && and || operations work. Using || will cause the loop to continue until both conditions are false. Using && will cause the loop to continue until either condition is false.
In your case, you've used || so the loop will continue until a=5 AND b=true. Since b will never be true, you've ended up with an infinite loop.
I'm not sure the exact behavior you're looking for, but there are three similar options to write your example loop, depending on how you want the two conditions to behave:
Or
while(a != 5 || b != true) {
a++;
}
The loop will continue if: a != 5 evaluates "true" or b!= true evaluates "true" or both a != 5 and b!= true evaluates "true". The first time both expressions evaluate to "false", the loop will exit.
And
while(a != 5 && b != true) {
a++;
}
The loop will continue if both a != 5 and b!= true evaluates "true". The first time one or both of these expressions evaluates to "false", the loop will exit.
XOR
while((a != 5 && b != true) || (a == 5 && b == true )) {
a++;
}
The loop will continue if both a != 5 and b!= true evaluate "true", or both evaluate "false". The first time exactly one these two expressions evaluates to "false", the loop will exit.
You have an infinite loop because b is always false, and hence, the loop continues since || means OR, and you have implemented it to continue as long as a is not 5 OR b is not true.

Why obvious False result of logical AND operation cancels out FOR loop iteration

My question is why this condition in a for loop makes it cancel out iteration, however it seems to me that condition is fulfilled?! If I try with one of two given variables without using AND operator looping works and continues infinitely.
bool a = false;
bool b = false;
for (; a && b == false; )
{
Console.WriteLine("");
}
This condition
a && b == false
means
a && (b == false)
Since && does short circuit evaluation, the first false will result in false for whole expression, and thus there is no need to evaluate second expression.
Also to add, even with a single & (which doesn't perform short circuit evaluation, your complete condition will result in false.
If you want to compare both a and b to false you can do:
a == false && b == false
or
!a && !b
You should also consider using a while loop, if there is no iteration variable involved.
https://msdn.microsoft.com/en-us/library/aa691323%28v=vs.71%29.aspx
Because the == is evaluated before &&, the condition is a && (b == false)
so false.

C# conditional AND (&&) OR (||) precedence

We get into unnecessary coding arguments at my work all-the-time. Today I asked if conditional AND (&&) or OR (||) had higher precedence. One of my coworkers insisted that they had the same precedence, I had doubts, so I looked it up.
According to MSDN AND (&&) has higher precedence than OR (||). But, can you prove it to a skeptical coworker?
http://msdn.microsoft.com/en-us/library/aa691323(VS.71).aspx
bool result = false || true && false; // --> false
// is the same result as
bool result = (false || true) && false; // --> false
// even though I know that the first statement is evaluated as
bool result = false || (true && false); // --> false
So my question is how do you prove with code that AND (&&) has a higher precedence that OR (||)? If your answer is it doesn't matter, then why is it built that way in the language?
Change the first false by true. I know it seems stupid to have (true || true) but it proves your point.
bool result = true || true && false; // --> true
result = (true || true) && false; // --> false
result = true || (true && false); // --> true
If you really want to freak him out try:
bool result = True() | False() && False();
Console.WriteLine("-----");
Console.WriteLine(result);
static bool True()
{
Console.WriteLine(true);
return true;
}
static bool False()
{
Console.WriteLine(false);
return false;
}
This will print:
True
False
False
-----
False
Edit:
In response to the comment:
In C#, | is a logical operator that performs the same boolean logic as ||, but does not short-circuit. Also in C#, the | operator has a higher precedence than both || and &&.
By printing out the values, you can see that if I used the typical || operator, only the first True would be printed - followed by the result of the expression which would have been True also.
But because of the higher precedence of |, the true | false is evaluated first (resulting in true) and then that result is &&ed with false to yield false.
I wasn't trying to show the order of evaluation, just the fact that the right half of the | was evaluated period when it normally wouldn't be :)
Wouldn't this get you what you're after? Or maybe I'm missing something...
bool result = true || false && false;
You don't prove it with code but with logic. AND is boolean multiplication whereas OR is boolean addition. Now which one has higher precedence?
false || true && true
Yields: true
false && true || true
Yields: true
You cannot just show the end result when your boolean expressions are being short-circuited. Here's a snippet that settles your case.
It relies on implementing & and | operators used by && and ||, as stated in MSDN 7.11 Conditional logical operators
public static void Test()
{
B t = new B(true);
B f = new B(false);
B result = f || t && f;
Console.WriteLine("-----");
Console.WriteLine(result);
}
public class B {
bool val;
public B(bool val) { this.val = val; }
public static bool operator true(B b) { return b.val; }
public static bool operator false(B b) { return !b.val; }
public static B operator &(B lhs, B rhs) {
Console.WriteLine(lhs.ToString() + " & " + rhs.ToString());
return new B(lhs.val & rhs.val);
}
public static B operator |(B lhs, B rhs) {
Console.WriteLine(lhs.ToString() + " | " + rhs.ToString());
return new B(lhs.val | rhs.val);
}
public override string ToString() {
return val.ToString();
}
}
The output should show that && is evaluated first before ||.
True & False
False | False
-----
False
For extra fun, try it with result = t || t && f and see what happens with short-circuiting.

What does this snippet of C# code do?

What does result.IsVisible equal?
if(a==b)
result.IsVisible = obj1.status.abc_REPORT == 'Y'
&& obj1.AnotherValue.ToBoolean() == false;
That depends on the values of obj1.status.abc_Report and obj1.AnotherValue.ToBoolean() (and it all depends on whether a==b or not).
I'm not quite sure of what the real question is here - which bit is confusing you?
One bit which may be confusing you is the shortcircuiting && operator (and possibly the lack of bracing!)
The && operator will only evaluate its right hand side if the left hand side evaluates to true: and the overall result of the expression is true if and only if both sides evaluates to true. (I'm assuming no strange user-defined conversions here.)
So another way of writing it would be:
if (a == b)
{
bool visibility = false;
if (obj1.status.abc_REPORT == 'Y')
{
if (obj1.AnotherValue.ToBoolean() == false)
{
visibility = true;
}
}
result.IsVisible = visibility;
}
Note that a condition comparing Booleans, like this:
obj1.AnotherValue.ToBoolean() == false
would usually be written like this:
!obj1.AnotherValue.ToBoolean()
(Note the exclamation mark at the start - the logical "not" operator.)
The same as this, in many less lines:
if (a==b) {
if (obj1.status.abc_REPORT == 'Y') {
if (obj1.AnotherValue.ToBoolean() == false) {
result.IsVisible = true;
}
else {
result.IsVisible = false;
}
}
else {
result.IsVisible = false;
}
}
In simple words:
If a is equal to b:
result will be visible only if:
object1's status's abc_report is Yes(Y = Yes most probably) AND object1's other value cannot be converted to a Boolean
I'm guess result.IsVisible is a boolean
It will be true if the following conditions are true:
obj1.status.abc_REPORT == 'Y'
and
obj1.AnotherValue.ToBoolean() == false
Also, a == b must be true to enter the initial if
lets go line by line:
if(a==b)
obvious if value of a equals value of b the execute following line
result.IsVisible = obj1.status.abc_REPORT == 'Y'
&& obj1.AnotherValue.ToBoolean() == false;
result is some object (maybe winforms controls etc) which has a property IsVisible set it to true if obj1.status.abc_REPORT is equal to 'Y' and also obj1.AnotherValue.ToBoolean() is equal to false;

Categories

Resources