in reply to Negative zero from a multiplication by a zero?

It's a little bit interesting that -2.0, -1.0 and -0.0, when multiplied by zero, are yielding 0 instead of -0.
It looks, at first glance, like a half-arsed stuff up.

But the very act of multiplying the NV's -2.0, -1.0 and -0.0 by any whole number sets the IV flags and places 0 in the IV (int) slot. The signedness of the zero is therefore lost. Signedness of zero, is defined only for floating point (float/double) zeroes - so the 0 in the IV slot will always be unsigned.

The other numbers, being non-integral values, will preserve their NV flags when mutliplied, and the value printed for them will be the value that's stored in the NV (double) slot - thus allowing for the appearance of -0 (when supported by the underlying conditions).

Cheers,
Rob
  • Comment on Re: Negative zero from a multiplication by a zero?

Replies are listed 'Best First'.
Re^2: Negative zero from a multiplication by a zero?
by ikegami (Patriarch) on Jun 10, 2009 at 02:43 UTC
    Interesting. I just figured they were getting stored as IVs, but that's not the case. That means you can't work around the problem by upgrading the vars to NVs since they already are!
    $ perl -MDevel::Peek -e'$x=-2.1; Dump $x; $x*=0; Dump $x' SV = NV(0x5291b8) at 0x504ca0 REFCNT = 1 FLAGS = (NOK,pNOK) NV = -2.1 SV = PVNV(0x507598) at 0x504ca0 REFCNT = 1 FLAGS = (NOK,pNOK) IV = -2 NV = -0 PV = 0 $ perl -MDevel::Peek -e'$x=-2.0; Dump $x; $x*=0; Dump $x' SV = NV(0x5291b8) at 0x504ca0 REFCNT = 1 FLAGS = (NOK,pNOK) NV = -2 SV = PVNV(0x507598) at 0x504ca0 REFCNT = 1 FLAGS = (IOK,pIOK) IV = 0 NV = -2 PV = 0
        If you were desperate, you could compile a perl with PERL_PRESERVE_IVUV turned off.

        Hey ... that works!! (No, I'm not desperate - just anal :-)

        Any arithmetic operation on IV's now seems to turn them into NV's so (-2 * 0) reports -0 even though the original operands are IV's.
        (2 * -0) reports 0, but that's to be expected given the underlying events.
        (2 * -0.0) does report -0, again as expected.

        One thing I did find while building this perl was that 'dmake test' reported 2 failures in the Devel::Peek tests - all other tests passed. I suspect those 2 Devel::Peek tests might be overlooking the possibility of NO_PERL_PRESERVE_IVUV being defined. I'll check that out properly later today, and submit a bug report.

        Cheers,
        Rob