Topic: Math eval order


Author: kanze@gabi-soft.fr (J. Kanze)
Date: 1995/06/26
Raw View
Steve Clamage (clamage@Eng.Sun.COM) wrote:
|> In article J5B@netcom.com, cpp@netcom.com (Robin Rowe) writes:
|> >
|> >If you look at page 207 of "C, A Reference Manual, 3rd Ed." by Harbison
|> >and Steele Jr. from Prentice-Hall, it clearly states that C may reorder
|> >operands under some conditions:
|> >
|> >"The compiler is free, for example, to evaluate (a+b)+(c+d) as if it were
|> >written (a+d)+(b+c) (assuming all variables have the same artithmetic
|> >type)."
|> >
|> >My question is, how does C++ behave? Does it have more restrictive, less
|> >restrictive, or the same rules with regard to this as C? I'm looking
|> >for an authoritative answer, not opinions.

|> Here's what the C++ draft standard says, clause 5, paragraph 4:

|> "Operators can be regrouped according to the usual mathematical rules only
|> where the operators really are associative or commutative.  Overloaded
|> operators are never assumed to be associative or commutative. Except where
|> noted, the order of evaluation of operands of individual operators and
|> subexpressions of individual expressions, and the order in which side
|> effects take place, is unspecified."

Which means, in sum:

1. Operators on unsigned may be regrouped.

2. Operators on signed may be regrouped, *IF* the compiler can assert
that the results will be the same.  On a 2s complement machine without
overflow trapping, for example, they can be regrouped.

3. Operators on floating point may never be regrouped, except maybe
special cases involving constants (in practice, anyway).

4. Operators on pointers: very machine dependant, but I suspect that
on most machines (including Intel), this would fall under 1 or 2.

5. All other operators are user defined, and may not be regrouped.

(The above, of course, only concerns addition.)
--
James Kanze           (+33) 88 14 49 00          email: kanze@gabi-soft.fr
GABI Software, Sarl., 8 rue des Francs Bourgeois, 67000 Strasbourg, France
Conseils en informatique industrielle--
                             --Beratung in industrieller Datenverarbeitung





Author: cpp@netcom.com (Robin Rowe)
Date: 1995/06/22
Raw View
In article <3saj54$1d3@cmcl2.nyu.edu>, Ed Osinski <osinski@cs.nyu.edu> wrote:
>Again, read the original quote, and what I said.  Clearly, the results
>do differ, and therefore the compiler would not allowed to rearrange
>the order.  (At least, according to the quote.  I don't know what the
>draft standard says, but I would guess that it would say pretty much
>the same thing.)

If you look at page 207 of "C, A Reference Manual, 3rd Ed." by Harbison
and Steele Jr. from Prentice-Hall, it clearly states that C may reorder
operands under some conditions:

"The compiler is free, for example, to evaluate (a+b)+(c+d) as if it were
written (a+d)+(b+c) (assuming all variables have the same artithmetic
type)."

My question is, how does C++ behave? Does it have more restrictive, less
restrictive, or the same rules with regard to this as C? I'm looking
for an authoritative answer, not opinions.

Robin
--
-----
Robin Rowe       cpp@netcom.com       408-626-6646          Carmel, CA
Rowe Technology  C++ Design/Training  Email for sample C++ Newsletter!





Author: osinski@valis.cs.nyu.edu (Ed Osinski)
Date: 1995/06/22
Raw View
In article <JR.95Jun21164344@efixid.efi.sintef.no>, Jarand.Roynstrand@efi.sintef.no writes:
|> In article <3s7l4u$a2g@cmcl2.NYU.EDU> osinski@valis.cs.nyu.edu (Ed Osinski) writes:
|>
|> |> In article <cppDAGDwL.BxC@netcom.com>, cpp@netcom.com (Robin Rowe) writes:
|> |> |> << Operators can be regrouped according to the usual mathematical
|> |> |> rules only where the operators really are associative or
|> |> |> commutative. >>
|> |> |>
|> |>
|> |> According to the quote above, it seems clear that the compiler is
|> |> allowed to regroup the operators as long as it has no effect on the
|> |> result in a legal program.
|>
|> Yes, but what does "really associative " mean.
|>
|> It is clear that x*y/z should mean (x*y)/z, which is very different from
|> x*(y/z).
|>
|> But what about
|>
|> x+y+z ?
|>
|> I read this as (x+y)+z, which in theory is the same as x+(y+z), but for
|> numerical reason they may differ.

Since the '+' used in a program is not the mathematical '+', how the
mathematical '+' behaves has no bearing on this discussion.  The fact
that the mathematical '+' is commutative is irrelevant.  What matters
is the behavior of the actual '+' as implemented on an actual machine.

|> Try x=1e100, y=-1e100, z=1. (if tese number are representable on your
|> system.
|>
|> (1e100+(-1e100))+1 = 1
|> 1e100+(-1e100+1) = 0 on most systems.
|>
|> Does the standard tell you how this is to be evaluated?

Again, read the original quote, and what I said.  Clearly, the results
do differ, and therefore the compiler would not allowed to rearrange
the order.  (At least, according to the quote.  I don't know what the
draft standard says, but I would guess that it would say pretty much
the same thing.)

--
---------------------------------------------------------------------
 Ed Osinski
 Computer Science Department, New York University
 E-mail:  osinski@cs.nyu.edu
---------------------------------------------------------------------
"No, no, no, don't tug on that. You never know what it might be attached to."
 -- Buckaroo Bonzai to assistant during brain surgery





Author: clamage@Eng.Sun.COM (Steve Clamage)
Date: 1995/06/22
Raw View
In article J5B@netcom.com, cpp@netcom.com (Robin Rowe) writes:
>
>If you look at page 207 of "C, A Reference Manual, 3rd Ed." by Harbison
>and Steele Jr. from Prentice-Hall, it clearly states that C may reorder
>operands under some conditions:
>
>"The compiler is free, for example, to evaluate (a+b)+(c+d) as if it were
>written (a+d)+(b+c) (assuming all variables have the same artithmetic
>type)."
>
>My question is, how does C++ behave? Does it have more restrictive, less
>restrictive, or the same rules with regard to this as C? I'm looking
>for an authoritative answer, not opinions.

Here's what the C++ draft standard says, clause 5, paragraph 4:

"Operators can be regrouped according to the usual mathematical rules only
where the operators really are associative or commutative.  Overloaded
operators are never assumed to be associative or commutative. Except where
noted, the order of evaluation of operands of individual operators and
subexpressions of individual expressions, and the order in which side
effects take place, is unspecified."

---
Steve Clamage, stephen.clamage@eng.sun.com







Author: cpp@netcom.com (Robin Rowe)
Date: 1995/06/20
Raw View
<< Operators can be regrouped according to the usual mathematical
rules only where the operators really are associative or
commutative. >>

Hi. I've read this several times, each time becoming less certain of the
meaning. Does C++ have the same or different rules for operators as C?

1. If I have an expression x*y/z does C++ evaluate left to right or may it
reorder the operands as though it was x*(y/z)?

2. If I write an expression as x*(y/z) may the compiler ignore the
parentheses and evaluate it left to right?

Thanks.

Robin
--
-----
Robin Rowe       cpp@netcom.com       408-626-6646          Carmel, CA
Rowe Technology  C++ Design/Training  Email for sample C++ Newsletter!





Author: osinski@valis.cs.nyu.edu (Ed Osinski)
Date: 1995/06/20
Raw View
In article <cppDAGDwL.BxC@netcom.com>, cpp@netcom.com (Robin Rowe) writes:
|> << Operators can be regrouped according to the usual mathematical
|> rules only where the operators really are associative or
|> commutative. >>
|>
|> Hi. I've read this several times, each time becoming less certain of the
|> meaning. Does C++ have the same or different rules for operators as C?
|>
|> 1. If I have an expression x*y/z does C++ evaluate left to right or may it
|> reorder the operands as though it was x*(y/z)?
|>
|> 2. If I write an expression as x*(y/z) may the compiler ignore the
|> parentheses and evaluate it left to right?

According to the quote above, it seems clear that the compiler is
allowed to regroup the operators as long as it has no effect on the
result in a legal program.

--
---------------------------------------------------------------------
 Ed Osinski
 Computer Science Department, New York University
 E-mail:  osinski@cs.nyu.edu
---------------------------------------------------------------------
"No, no, no, don't tug on that. You never know what it might be attached to."
 -- Buckaroo Bonzai to assistant during brain surgery





Author: Jarand.Roynstrand@efi.sintef.no
Date: 1995/06/21
Raw View
In article <3s7l4u$a2g@cmcl2.NYU.EDU> osinski@valis.cs.nyu.edu (Ed Osinski) writes:

|> In article <cppDAGDwL.BxC@netcom.com>, cpp@netcom.com (Robin Rowe) writes:
|> |> << Operators can be regrouped according to the usual mathematical
|> |> rules only where the operators really are associative or
|> |> commutative. >>
|> |>
|>
|> According to the quote above, it seems clear that the compiler is
|> allowed to regroup the operators as long as it has no effect on the
|> result in a legal program.

Yes, but what does "really associative " mean.

It is clear that x*y/z should mean (x*y)/z, which is very different from
x*(y/z).

But what about

x+y+z ?

I read this as (x+y)+z, which in theory is the same as x+(y+z), but for
numerical reason they may differ.

Try x=1e100, y=-1e100, z=1. (if tese number are representable on your
system.

(1e100+(-1e100))+1 = 1
1e100+(-1e100+1) = 0 on most systems.

Does the standard tell you how this is to be evaluated?

--

   ====         Best regards
     \\                              Jarand Roeynstrand
      \\                           DIG-hackers department
     \====\
  .,;,\    \                     EFI
,;;;;;;;;,_/     ____          N-7034 Trondheim
           |    |              Norway
           |    |
            \__/

Phone:  +47-73 59 72 75           Email: jr@efi.sintef.no