How long does it take you to grok this code?
by Michael S. Kaplan, published on 2005/09/16 19:42 -04:00, original URI: http://blogs.msdn.com/b/michkap/archive/2005/09/16/469651.aspx
You have to be honest if you want to play on this one. :-)
Look at the snippet of code below, and tell me how long it takes you to grok the intent:
if (!((dwFlags & (GLOBAL_FLAG1 | GLOBAL_FLAG2)) && (!(dwFlags & GLOBAL_FLAG3)))) {
break;
}
I got it, but it really did take me a couple of minutes and a white board.
This is not an interview question I would ever give, but it is of a type that I have been given once or twice....
# Maurits [MSFT] on 16 Sep 2005 8:09 PM:
break if flag three is on.
break if flags one and two are both off.
(I despise negative assertions...)
A simpler rewrite:
if (dwFlags & GLOBAL_FLAG3) { break; }
if (dwFlags & (GLOBAL_FLAG1 | GLOBAL_FLAG2) == 0) { break; }
# CornedBee on 16 Sep 2005 8:31 PM:
One minute, but I've got a lot of practice in this.
# James Todd on 16 Sep 2005 9:42 PM:
30 seconds.
Really. I used my stopwatch.
If the flags have (FLAG1 and FLAG2), and it does NOT have FLAG3, then continue. Otherwise, break.
# Centaur on 17 Sep 2005 1:00 AM:
Did not time, but I think I did it in under a minute. Although I’d say either the condition or its two subconditions want to move into separate boolean functions (possibly leaving the outermost ! and && behind).
if (!predicate1(dwFlags) || !predicate2(dwFlags)) break;
# An Phu on 17 Sep 2005 1:11 AM:
Maurits got it right.
It took me notepad.exe and two minutes.
# Maurits [MSFT] on 17 Sep 2005 2:29 AM:
;)
# Mike Weller on 17 Sep 2005 5:01 AM:
30 seconds, but it's not really that hard if you've done alot of this stuff.
# Tim Smith on 17 Sep 2005 10:46 AM:
Maurits goofed. His second statement should be:
if ((dwFlags & (GLOBAL_FLAG1 | GLOBAL_FLAG2)) == 0) { break; }
If you don't mix your logical operators with numeric results and use the !(a&b) = (!a|!b) rule, you can write:
if ((dwFlags & (GLOBAL_FLAG1 | GLOBAL_FLAG2)) == 0 || (dwFlags & GLOBAL_FLAG3) != 0)
{
break;
}
while is much easier to read in my opinion.
# Maurits [MSFT] on 17 Sep 2005 11:43 AM:
Yup, == binds more tightly than &. My bad.
# Adi Oltean on 20 Sep 2005 3:45 AM:
>>> if (!((dwFlags & (GLOBAL_FLAG1 | GLOBAL_FLAG2)) && (!(dwFlags & GLOBAL_FLAG3)))) {
break;
}
Whenever I see (!(expr1 && expr2)) I immediately try to reduce it as (!expr1 || !expr2).
In our case, this helps a lot since expr2 already contains !, so the original "if" statement simplifies to:
if ((dwFlags & (GLOBAL_FLAG1 | GLOBAL_FLAG2) == 0) || (dwFlags & GLOBAL_FLAG3))) {
break;
}
which says that if either dwFlags doesn't contain both FLAG1 & FLAG2, or if dwFlags contains FLAG3, then break.
Generally, an expression is easier to follow up if you reduce it to the normal form:
(expr11 && expr12 && ... )
|| (expr21 && expr22 && ... )
...
|| (exprN1 && exprN2 && ... )
Tanveer Badar on 30 Dec 2007 8:38 AM:
~25 seconds. I had to read three times highlighting various parenthesis with mouse.
But then, I also finished Harry Potter and the Deathly Hallows in 10:45 hours. :)
Please consider a
donation to keep this archive running, maintained and free of advertising.
Donate €20 or more to receive an offline copy of the whole archive including all images.
go to newer or older post, or back to index or month or day