C #: function evaluation order (vs C)

Take the following C code (K & R p. 77):

push(pop() - pop()); /* WRONG */ 

The book says that since - and / are not commutative operators, the order in which 2 pop functions are evaluated (obviously, to get the correct result) is needed ... and therefore, you first have to put the result of the first function in a variable, and then go to arithmetic, for example:

 op2 = pop(); push(op2 - pop()); 

This is apparently due to the fact that the compiler cannot guarantee in which order the functions are evaluated (... why?)


My question is, does C # do the same? as in, do I need to worry about this while working with C #? and, for that matter, any of the other higher-level languages?

+5
c math c #
source share
8 answers

In C #, it is from left to right: http://blogs.msdn.com/oldnewthing/archive/2007/08/14/4374222.aspx


Re: C ++ order

This is apparently due to the fact that the compiler cannot guarantee in which order the functions are evaluated (... why?)

Any specific compiler can guarantee the order. The problem is that the language specification does not determine the order, so each compiler can do whatever it wants. This means that you need to add a sequence point between two method calls if you want to guarantee order.

+11
source share

To answer the question of why C does not determine the order of work, it is simply because the inventors of C decided that it would be useful to provide compiler developers the opportunity to optimize the evaluation of the expression. They also decided that it was more valuable than giving programmers confidence in evaluating expressions.

Remember that when C was originally developed, machines were much less capable than they are today, and there was interest in providing compilers with optimizations. Nowadays, often more attention is paid to safer, more predictive code.

+5
source share

From Incredible Adventures in Coding: Priority Against Associativity and Order :

Another way to look at this is that the rule in C # does not “make the brackets first,” but rather bracket everything, and then recursively apply the rule “evaluate the left side, then evaluate the right side, and then perform the operation” .

+2
source share

No, C # does not do the same. It does not use bounds on the bounds like C, where the order of execution between bounds is undefined. The expression evaluates from left to right, as you would expect.

If you are ever unsure of the execution order or want to make the code more understandable, you should use a local variable for the intermediate result. Local variables are very cheap to allocate because they are allocated on the stack, and in some cases the compiler can even put the variable in the register so that it is not allocated at all. In addition, depending on how the expression looks like a compiler, you may need to use a local variable to store the result of the intermediate information.

+2
source share

The order of evaluation is well defined in C # in all cases and from left to right. From the C # language specification (§7.3):

The procedure for evaluating operators in an expression is determined by the priority and associativity of the operators (clause 7.2.1). The operands in the expression evaluate from left to right. For example, in F (i) + G (i ++) * H (i), method F is called using the old value of i, then method G is called with the old value of i, and finally, method H is called with the new value of i. This is separate from and not related to operator priority.

In the case of C ++, this does not mean that the order cannot be determined; this, to allow the order to be undefined, allows the compiler to better optimize the code.

+1
source share

The book says that since - and / are not commutative operators, the order in which 2 pop functions are evaluated is necessary (obviously, to get the correct result) ... and therefore, you must put the result of the first function in a variable first, and then go on to arithmetic.

This is not entirely correct. K & R allowed the rearrangement of commutative operators ( done with ANSI C ). Since suibtraction is not commutative, it does not rebuild ... by this rule, at least.

(Un), fortunately, C also does not determine the order of evaluation (outside a rather small area ), which means that the compiler can call these functions in any order (as long as the result pop() - pop() is fully evaluated to call push() )

What - in this case leads to the same problem - but for a different reason.

+1
source share

I believe in C # the argument list is evaluated in order from left to right.

0
source share

The color surprised me, but, apparently, C # does the “right” thing and evaluates from left to right:

 void Main() { Console.WriteLine(Pop() - Pop()); // Prints -1 } // Define other methods and classes here bool switchVar = true; int Pop() { int ret; if (switchVar) ret = 1; else ret = 2; switchVar = !switchVar; return ret; } 
0
source share

All Articles