C

edited December 2009 in Chit chat
is this a valid instruction?
A + B;
If I assign 3 to A and 2 to B;
and then "A + B;",
then A should equal 5, and B equal 2.

Correct?
Post edited by wilsonsamm on

Comments

  • edited December 2009
    It depends what class A and B are, and if the '+' operator changes the class in the calculation.

    But as you said C (which doesn't do classes, unlike its bigger brothers C++ and C#), then "A+B" will always evaluate to (A+B), leaving A and B themselves unchanged.

    If the line of C was *just* "A+B", then it wouldn't do anything practical.
  • edited December 2009
    so to add B onto A, I need to put this, am I right?
    A = A + B;
  • edited December 2009
    wilsonsamm wrote: »
    so to add B onto A, I need to put this, am I right?
    A = A + B;

    Yes, or you can save precious keystrokes and use
    A += B;
    
    as well.
  • edited December 2009
    If both of these are integers, then what happens if it's carried over?
    Can I check for this case in the same way that I can with assembler?
  • edited December 2009
    NickH wrote: »
    It depends what class A and B are, and if the '+' operator changes the class in the calculation.

    But this is something a programmer should never do as it completely changes the semantics of +. + should never change any of the objects involved in the operation. As you say, this is C so no classes are involved but C++ extends C semantics to classes; it wasn't intended to change them and none of the standard libraries bundled with C++ will either.
    wilsonsamm wrote: »
    is this a valid instruction?
    A + B;
    

    Yes it is. The resulting code will compute A+B and then throw away the result. Neither A or B will change. In other words, the code is useless on its own and a modern C compiler will just not bother to generate code for it.

    In C++, A and B can be something other than numbers (objects of a particular user-defined class as previously mentioned) and the compiler will create a temporary object that holds the result of A+B which it will then throw away. It is possible that a programmer wanted to be an arse and needlessly defined the + operation to have side effects on either A or B. Such a case would be clear to the compiler through the operator+ definition and the compiler will know that the code generated was not completely useless and should include the portion that changes A and/or B. Such a programmer should be fired ASAP because such code would cause major maintenance problems down the line :-)
  • edited December 2009
    wilsonsamm wrote: »
    If both of these are integers, then what happens if it's carried over?
    Can I check for this case in the same way that I can with assembler?

    If it carries over it just rolls over. There is nothing in the standard C language that will automatically check for overflow or underflow, just as with an assembly add or sub instruction.

    Different compilers may have non-portable ways to detect these things but one should have good reason to use non-portable features to do anything. Such as your code will never be ported to another cpu architecture (and there have been failures in the past when this did happen, contrary to the original programmers' expectations). Anyway it's actually not that common to be in a position to have to worry about such things. The usual solution is to use a bigger integer type or check the values beforehand to know whether an operation will overflow or not.
  • edited December 2009
    If it carries over it just rolls over. There is nothing in the standard C language that will automatically check for overflow or underflow, just as with an assembly add or sub instruction.

    Except that our beloved Z80 (and most other CPUs I assume) do have something that provides you with a check - the Carry (C) flag (which also works as a Borrow Flag in a SUB/SBC instruction).

    It is automatic in the sense that the C flag is set automatically and you are free to test it after the op.
  • edited December 2009
    In C you can check if signed integers have overflowed as follows:

    If the sign (SGN) of the two operands are opposite (one +ve and one -ve) then you will not get an overflow.

    If the signs are both positive and the result is LESS than zero then an overflow (carry) has occurred.

    If the signs are both negative and the result is GREATER than zero then an overflow (borrow) has occurred.

    This algorithm would work perfectly well on the spectrum with 8-bit registers but the carry flag gives you an easy way to check.
  • edited December 2009
    BloodBaz wrote: »
    Except that our beloved Z80 (and most other CPUs I assume) do have something that provides you with a check - the Carry (C) flag (which also works as a Borrow Flag in a SUB/SBC instruction).

    It is automatic in the sense that the C flag is set automatically and you are free to test it after the op.

    carry and overflow flags. I misspoke a little -- the C code will translate into an asm add/sub/whatever and a rollover will occur, just as in asm.

    There are cpus / fpus that are capable of generating exceptions on overflow and those I'd cast the automatic detection variety :-)

    If we are restricting ourselves to the z80 (or spectrum) and the z88dk compiler, z88dk provides the non-portable 'iferror' and 'ifnerror' to detect the state of the carry flag. An 'if error' right after an add or sub will probably catch the carry flag as set by the add or sub. There's no way to test the P/V flag but in both cases (carry or p/v) you can always dip into some inlined assembler to accompilsh that too.
Sign In or Register to comment.