question on a generic program logic issue (redux)

  • Follow


Hate it when I do this... send a message, immediately realize I forgot
something.  Repost, with an important edit.  See second of two
pseudocode examples, below....

I'm trying to figure out how to do something in code, fairly
efficiently, using fairly standard programming constructs.  The exact
language doesn't matter, could be C, C++, Java, Visual Basic, C#, etc.

The idea is this.  I want to have some code that basically says:

if (condition1 and/or condition2 and/or condition3) then�.

where the "and/or" is determined by some kind of flag that can be set
dynamically.  Viewed another way, in pseudocode, I want:

if 
(c1
use "and" if and_flag1=true else use "or" if or_flag1=true
c2
use "and" if and_flag2=true else use "or" if or_flag2=true
c3) then...

I'm trying to figure out how to code this efficienty using standard
kinds of procedural constructs:  if/then, if/then/else, case or switch
statements, etc.

I'm a hobbyist, not a pro, and a little rusty on my programming, and
just getting back into it.  So maybe I've forgotten some obvious way
to do this.  

I can come up with long, clunky approaches, but nothing elegant and
simple.  For example, I could use the flags to set up different
conditions in a switch statement, and then each case in the switch
statement represents a different combo of and/or flags;  but that gets
real long, especially if there's more than just three conditions.

If someone can show me some simple way to set this up, I'd be real
grateful.  


0
Reply null12 (104) 7/16/2011 6:41:20 AM

On 16/07/2011 07:41, NoName wrote:
> Hate it when I do this... send a message, immediately realize I forgot
> something.  Repost, with an important edit.  See second of two
> pseudocode examples, below....
>
> I'm trying to figure out how to do something in code, fairly
> efficiently, using fairly standard programming constructs.  The exact
> language doesn't matter, could be C, C++, Java, Visual Basic, C#, etc.
>
> The idea is this.  I want to have some code that basically says:
>
> if (condition1 and/or condition2 and/or condition3) then�.
>
> where the "and/or" is determined by some kind of flag that can be set
> dynamically.  Viewed another way, in pseudocode, I want:
>
> if
> (c1
> use "and" if and_flag1=true else use "or" if or_flag1=true
> c2
> use "and" if and_flag2=true else use "or" if or_flag2=true
> c3) then...
>

My first reaction is to wonder if what you are trying to do is actually 
the best way to tackle whatever problem you have. Often inelegant code 
is the result of a wrong approach. However let me assume that you really 
do need to do what you outline.

My next comment is that a transparent solution (one where it is easy to 
see what is being done) is easier to maintain and the loss in efficiency 
is likely to be small.

Next we need to distinguish between speed an space. Frequently one can 
trade one for the other. However modern optimising compilers often 
recover a great deal of efficiency if they can analyse your code.

Any way here is what I would try (in C++).

int select(flag1);
select += flag2 << 1;
// the above assumes that flag2 is an integer type
//  rather than a pure bool
// Now the four conditions are numbered 0 to 3
// can extend this to more options but does not scale well
bool doit(false);
switch(select){
    case 0: if(condition1 or condition2 or condition3) doit=true;
            break;
    case 1: if(condition1 and condition2 or condition3) doit=true;
            break;
    case 2: if(condition1 or condition2 and condition3) doit=true;
            break;
    case 3: if(condition1 and condition2 and condition3) doit=true;
            break;
    default: throw("something is terribly wrong");
}
if(doit){
//    whatever
}

I think it is very unlikely that a different approach will result in a 
measurable improvement of performance. Where performance is acceptable, 
I place clarity of code (and hence maintainability) very high in my 
priorities for good code. It is a common fault with hobbyist programmers 
(note that I have never written a program for financial gain) to try to 
produce the ultimate efficient program. Usually the time taken to do 
this is time badly spent. Save as much as 1 second in runtime, but take 
3 hours programming time to do it and your program will have to run over 
10000 times for any net gain. Few hobbyist programs run even 1000 times.

I hope the above proves helpful.
Francis



0
Reply francis.glassborow (32) 7/16/2011 11:09:22 AM


NoName <null@null.com> writes:
<snip>
> I'm trying to figure out how to do something in code, fairly
> efficiently, using fairly standard programming constructs.  The exact
> language doesn't matter, could be C, C++, Java, Visual Basic, C#, etc.
>
> The idea is this.  I want to have some code that basically says:
>
> if (condition1 and/or condition2 and/or condition3) then….
>
> where the "and/or" is determined by some kind of flag that can be set
> dynamically.  Viewed another way, in pseudocode, I want:
>
> if 
> (c1
> use "and" if and_flag1=true else use "or" if or_flag1=true
> c2
> use "and" if and_flag2=true else use "or" if or_flag2=true
> c3) then...

I'd use functions:

  bool fn_and(bool a, bool b) { return a && b; }
  bool fn_or(bool a, bool b)  { return a || b; }

Then the simplest form is:

  (flag11 ? fn_and : fn_or)((flag2 ? fn_and : fn_or)(c1, c2), c3)

Obviously you can tidy this up.  Whatever function determines flag1 and
flag2 could simply return a pointer to the desired operation, or you
could put the function pointers into variables to avoid having
conditional expressions in the function position:

  typedef bool boolean_op(bool, bool);

  boolean_op *op1 = flaf1 ? fn_and : fn_or;
  boolean_op *op2 = flag2 ? fn_and : fn_or;

  if (op1(op2(c1, c2), c3)) ...

<snip>
-- 
Ben.
0
Reply ben.usenet (6516) 7/16/2011 11:42:55 AM

NoName wrote:


> where the "and/or" is determined by some kind of flag that can be set
> dynamically.  Viewed another way, in pseudocode, I want:
>
> if
> (c1
> use "and" if and_flag1=true else use "or" if or_flag1=true
> c2
> use "and" if and_flag2=true else use "or" if or_flag2=true
> c3) then...

As others will state -- correctly -- clarity is /probably/ the most important 
thing here.

To compute "if f then (x and y) else (x or y)", the C/Java/etc idiom:

    f ? (x && y) : (x || y)

will probably help.  Note that because of short-circuit evaluation, f and x are 
evaluated only once each, and y may not be evaluated at all.

If you need a chain of nested such expressions, then consider using temporary 
variables rather than complicated nested expressions.

    r2 = f1 ? (x1 && y1) : (x1 || y1);
    r3 = f2 ? (r2 && y2) : (r2 || y2);
    r4 = f3 ? (r3 && y3) : (r3 || y3);
    ...

Alternatively define a function:

    bool and_or_or(bool useAnd, bool x, bool y)
    {
        if (useAnd)
            return a && y;
        else
            return x || y;
    }

which you can nest more readily than the "raw" operator combination.

Lastly, it MIGHT be that you want to perform lots of these operations in 
parallel on bitmaps of boolean values (say expressed as integers), if so you 
can compute the bitwise equivalent of your operator with (arrived at by much 
tedious boolean algebra -- in which I can use the practice):
        f ^ ((f ^ x) | (x ^ y))

The above expression actually works on booleans too, but is much too obscure to 
use unless you have to. 


0
Reply chris.uppal (3970) 7/16/2011 12:49:00 PM

OP:  Thanks, all, these are very good suggestions.

On Sat, 16 Jul 2011 02:41:20 -0400, NoName <null@null.com> wrote:

0
Reply null12 (104) 7/16/2011 3:43:48 PM

On Jul 16, 7:41=A0am, NoName <n...@null.com> wrote:
> The idea is this. =A0I want to have some code that basically says:
>
> if (condition1 and/or condition2 and/or condition3) then=85.
>
> where the "and/or" is determined by some kind of flag that can be set
> dynamically. =A0Viewed another way, in pseudocode, I want:

If you can guarantee that the conditions are 0 or 1, then a simple

if (c1 + c2 + c3 <=3D x)

will give you "or" when x is 1 and "and" when x is 3.
0
Reply gw7rib (463) 7/16/2011 4:37:20 PM

On Sat, 16 Jul 2011 02:41:20 -0400, NoName <null@null.com> wrote:

>Hate it when I do this... send a message, immediately realize I forgot
>something.  Repost, with an important edit.  See second of two
>pseudocode examples, below....
>
>I'm trying to figure out how to do something in code, fairly
>efficiently, using fairly standard programming constructs.  The exact
>language doesn't matter, could be C, C++, Java, Visual Basic, C#, etc.
>
>The idea is this.  I want to have some code that basically says:
>
>if (condition1 and/or condition2 and/or condition3) then�.
>
>where the "and/or" is determined by some kind of flag that can be set
>dynamically.  Viewed another way, in pseudocode, I want:
>
>if 
>(c1
>use "and" if and_flag1=true else use "or" if or_flag1=true
>c2
>use "and" if and_flag2=true else use "or" if or_flag2=true
>c3) then...
>
>I'm trying to figure out how to code this efficienty using standard
>kinds of procedural constructs:  if/then, if/then/else, case or switch
>statements, etc.
 

I'm sorry but I'm having problems understanding exactly what you want,
i.e., what the code is supposed to do.  The statement

if (condition1 and/or condition2 and/or condition3) then

seems fairly clear - we have three (n) conditions with a mystery
operator called "and/or".  By the way, "and/or" had better be
associative or else you have a mess.  

The pseudo code is unclear, at least to me.  What does it mean to 'use
"and"' and 'use "or"'?  I'm assuming that your c1, c2, and c3 are the
condition1, condition2, and condition3 from the first statement and
that they are boolean values.  Now where do "and_flag1" etc come from?

One issue is that you don't index your mystery operators.  That is,
what you actually want is something like

"if (c1 op1 c2 op2 c3) then"

where c1 and c2 are boolean values and op1 and op2 are conditionally
operators.  This brings up something else; as far as I can tell there
is nothing to "use" if and_flag and or_flag are both false.  Let's
call this case bogus.  We have four cases for op1:

  and_flag  op_flag   operator
     T        T         and
     T        F         and
     F        T         or
     F        F         bogus

I would think that "c1 op1 c2" would be false when op1 is bogus but
that's just speculation.  Ignoring the "bogus" case we still have to
check whether your operators are associative; otherwise you need a
definite order of application rule.  IIANM they are not associative.
Consider the expression c1 && c2 || c3.  It is an abbreviation either
for (c1 && c2) || c3 or for c1 && (c2 || c3); the two expressions must
evaluate the same if your and/or is associative.  They do not; when c1
is false and c2 and c3 are true the first expression evaluates true
and the second one false.

What this comes down to is this you should apply the conditions and
operators in a defined order.  Odds are you are assuming left to right
parsing but that's your pick.

Now as to code.  If you aren't averse to using functions I suggest a
function that looks like this:

bool andor (bool c1, bool c2, bool and_flag, bool or_flag)
{
    if (and_flag) return c1 && c2;
    if (or_flag)  return c1 || c2;
    return false;  /* Whatever you want for this case */
}

Then your code looks like this:

c = andor(c1,c2,and_flag1,or_flag1);
c = andor(c ,c2,and_flag2,or_flag2);
/* etc */
if (c) {/* then do it */}

Note: given that you are doing the and/or trick you must examine all
conditions.

If I misunderstood your intent, my apologies.

   
0
Reply cri (1432) 7/16/2011 9:28:45 PM

"NoName" <null@null.com> wrote in message
news:nhc2275ivjf8jcbf8lkjjsifui29n0u6g0@4ax.com...

> if
> (c1
> use "and" if and_flag1=true else use "or" if or_flag1=true
> c2
> use "and" if and_flag2=true else use "or" if or_flag2=true
> c3) then...

I've been trying to think of an application of 'operator variables', and
this might be it.. Although none of the languages you mentioned have them
(as functions perhaps, but not operators).

Assuming and_flagN and or_flagN are mutually exclusively (one will be True,
the other False), you have four combinations here, and the simplest way
might be to write all four lots separately:

if and_flag1 and and_flag2 then
   if c1 and c2 and c3 then ...
elsif and_flag1 and or_flag2 then
   if c1 and c2 or c3 then ...
elsif or_flag1 and and_flag2 then
   if c1 or c2 and c3 then ...
else
   if c1 or c2 or c3 then ...
endif

You then go on to say that you don't like this approach; well you might like
to ask the opinion of the people who have to read your code!

> I can come up with long, clunky approaches, but nothing elegant and
> simple.  For example, I could use the flags to set up different
> conditions in a switch statement, and then each case in the switch
> statement represents a different combo of and/or flags;  but that gets
> real long, especially if there's more than just three conditions.

So, you might have something like this:

 if c1 and c2 or c3 or c4 and c5 or c6 and c7 and c8 ...

depending on an array and_flag[] and or_flag[] (although it's really easier
to just have one array, if and_flag[i] is always 'not or_flag[i]').

But the more important question then is, what does it mean?!

Because you run into a problem with precedence: usually 'and' has a tighter
precedence than 'or'. That needs to be sorted out first.

In fact it also comes up with the simple 2-operator case; is it:

 if c1 or (c2 and c3)   // normal precedence

or:

 if (c1 or c2) and c3 ?

If you intend to use the natural precedence order, then /I think/ that makes
evaluating an arbitrary long sequence much more difficult (because you need
to evaluate the expression as a tree with many different arrangements).

(This is also a problem when I was thinking about operator variables: the
compiler needs to know at least the priority, or precedence level, of the
operator, even if it doesn't know the actual operator.)

-- 
Bartc 

0
Reply bc (2221) 7/18/2011 9:35:44 AM

7 Replies
38 Views

(page loaded in 0.243 seconds)

Similiar Articles:













7/24/2012 8:05:52 PM


Reply: