Rewrite Boolean Expression without Parentheses - boolean

I have a black box processing system that accepts boolean expressions but does not support parentheses. I want to input a boolean expression like this:
A && (B || C)
However, when I input it as:
A && B || C
it evaluates expressions as if I had entered:
(A && B) || C
Is there any way to rewrite my expression to get the desired behavior of A && (B || C) without parentheses? Thanks!

There's a relation between precedence but, you can use associative and distributive laws to resolve this.
A && B || A && C
Truth tables match.
Be careful when implementing this. Not all compilers and languages use the same precedence and evaluation order.

Edit: No left-right precedence, sorry.
Use the distributive law and the precedence of && to check if either both A and B is true or both A and C is true.
Solution
A && B || A && C
Distributive Law
x ^ (y v z) = (x ^ y) v (x ^ z)
x && (y || z) = (x && y) || (x && z)
function original(A, B, C) {
return A && (B || C);
}
function mySolution(A, B, C) {
return A && B || C && A;
}
console.log(original(true, true, true) == mySolution(true, true, true));
console.log(original(true, true, false) == mySolution(true, true, false));
console.log(original(true, false, true) == mySolution(true, false, true));
console.log(original(true, false, false) == mySolution(true, false, false));
console.log(original(false, true, true) == mySolution(false, true, true));
console.log(original(false, true, false) == mySolution(false, true, false));
console.log(original(false, false, true) == mySolution(false, false, true));
console.log(original(false, false, false) == mySolution(false, false, false));

Related

Simplifying a boolean expression with 4 variables

I can't figure this one out, I'm going insane looking through my textbook.
The expression is: (!w && !x && !y && z) || (w && !x && !y && z) || (x && z) || (x && y && !z)
Using distributive and compliment laws, I have narrowed it down to:
(!x && !y && z) || (x && z) || (x && y && !z)
But I can't narrow it any further! The answer is supposed to be (x && y) || ( !y && z) but I can't figure out what law would put me there. My teacher told me to use distributive but wouldn't help me further. That doesn't make any sense since there's nothing I can factor out and get rid of. What law am I supposed to use next?
You can expand xz to x(y + !y)z => xyz + x!yz.
Now you have !x!yz + xyz + x!yz + xy!z.
Then !x!yz + x!yz simplifies to !yz, and xyz + xy!z simplifies to xy,
giving the minimal expression.

Triggers, #instances in Z3

My problem comes from a large Boogie file. I'll just explain the relevant parts here.
I declare a new type Msg for messages which have 7 fields tID, stype, bal, acc, mbal, mval, val. These fields are declared as functions in Boogie. Then I declared 72 Msg constants M1, ..., M72 and corresponding values of their fields. You can see the following example:
type Msg;
const unique M1: Msg;
function tID (Msg) returns (int);
function stype (Msg) returns (Str);
function bal (Msg) returns (int);
function acc (Msg) returns (Proc);
function mbal (Msg) returns (int);
function mval (Msg) returns (Val);
function val (Msg) returns (Val);
axiom (tID (M1) == 1);
axiom (stype (M1) == s1a);
axiom (bal (M1) == 1);
axiom (acc (M1) == ProcNull);
axiom (mbal (M1) == -2);
axiom (mval (M1) == ValNull);
axiom (val (M1) == ValNull);
where Proc, Str are some types and s1a, ProcNull, ValNull are some constants. Then I declare an axiom which says that two messages m1, m2 are equal if and only if every field of m1, m2. This axiom uses a trigger MsgComp(m1, m2).
function MsgComp(m1, m2: Msg): bool { true }
axiom (forall m1, m2: Msg :: {MsgComp(m1, m2)}
m1 == m2 <==>
(tID(m1) == tID(m2) && stype(m1) == stype(m2) &&
acc(m1) == acc(m2) && bal(m1) == bal(m2) &&
mbal(m1) == mbal(m2) && mval(m1) == mval(m2) &&
val(m1) == val(m2)));
Then, I declare a new variable m and assign arbitrary values to its fields such that m equals M1 or M2. I don't say explicitly m == M1 || m == M2but we can prove this assertion (line 786) with the above axiom.
assert (MsgComp(cMsg, M1) && MsgComp(cMsg, M2) && (cMsg == M1 || cMsg == M2));
However, if I want to check whether m is one of M1, ..., M72, Boogie shows that the corresponding assertion might not hold.
assert (MsgComp(cMsg, M1) && ... && MsgComp(cMsg, M72) && (cMsg == M1 || ... || cMsg == M72));
And I found that if I check that assertion with at most 32 constants, Boogie can verify it. Why can't Boogie or Z3 verify it with more constants?
On my machine, the check does not succeed even for the case of two constants.
I was able to get both checks to pass by changing them to the following form
assert MsgComp(cMsg, M1) && MsgComp(cMsg, M2) ==> (cMsg == M1 || cMsg == M2);
(Notice that the && in the middle has been changed to ==>.)
This also works for the assertion with the 72 values.
I don't know why this change matters. It looks like the conjuncts are ignored or simplified away before triggering happens.

Comparing not then and vs and then not

I'm just wondering if there's a difference between an if or a while statement if the condition is either (!a && !b) (let's call this statement 1) or !(a && b) (let's call this statement 2).
I was thinking about it, and we have four combinations of a and b possible, and I think that the condition would be different if a != b. I'm just hoping someone can check my logic.
If a and b are both true, then statements 1 and 2 are both false. If a and b are both false, then statements 1 and 2 are both true. ?However, if a is true and b is false, or the inverse, then statement 1 is false, but statement 2 is true. Is this correct?
You are actually asking about a fundamental law of Boolean Algebra: De Morgan's Laws are very useful to know when re-working or simplifying conditionals.
De Morgan's Laws
!(a && b) = (!a || !b)
!(a || b) = (!a && !b)
Your intuition that your statements 1 and 2 might not be equivalent is correct. Working through the four possibilities of a and b above shows that the actual equivalencies are those given by De Morgan's Laws.
Key: ∧ is logical AND (&&); ∨ is logical OR (||).
Image source: http://ndp.jct.ac.il/tutorials/mavomath/node15.html
!(a && b) = !a || !b this does not equal !a && !b. In the first case if a or b is false then the result is true. In the second case both a and b must be false for the result to be true.
So as you say they have different results when a != b.

Writing (A && C) || (B && C) conditional shorter

(E.G. In Perl) When either condition A or condition B have the same consequence
if (A){
# Consequence X
}elsif (B){
# Consequence X
}
we can write
if ( A || B ) {
# Consequence X
}
How about we have the following condition: Either when A and C are true, or B and C are true, consequence C follows.
This can be written very long:
if ( A && C){
# Consequence X
} elsif (B && C ){
# consequence X
}
My question is, is there any way to write this shorter?
Something like this:
if ( (A && C) || (B && C) )
is syntactically ok ???
Yes.
if ( A && C){
# Consequence X
} elsif (B && C ){
# consequence X
}
is the same as:
if ( (A && C) || (B && C) ){
#Consequence X
}
And this avoids evaluating C twice:
if ( (A || B) && C){
#Consequence X
}
BTW, this is more like a logical question, the logic here isn't limited to Perl.
Try the following:
if (C && (A || B)) {
}

Confusing Boolean Expression

Given these values for the boolean variables x, y, and z:
x = true
y = false
z = true
Why does the following logical expression evaluate to true?
(x || !y) && (!x || z)
Substitute in the values of x, y, and z:
(true || !false) && (!true || true)
Flip the negated values:
(true || true) && (false || true)
Replace the ORed statements (if one side is true, the whole statement is true):
true && true
Replace the ANDed statement (if both sides are true, the whole statement is true):
true
True or False is always True. true || false
True and True is always True. true && true
X is true in the first grouping causing the first grouping to be true. Z is true in the second grouping causing the second grouping to be true. Therefore group 1 and group 2 are true.
(x || !y) && (!x || z)
= (T || !F) && (!T || T) <-- plug in x = T, y = F, z = T
= (T || T) && (F || T) <-- !F = T, !T = F
= T && T <- T || T = T, F || T = T
= T <- T && T = T
Actually, please tell us what's so confusing; I am slightly confused that you find it confusing at all.