in reply to Perl with precision

These numbers (ie: strings) may come from anywhere such as a database, a spread sheet etc What is the best way to clean them, add them, multiply them with confidence? :)

Your problem is artificial because you could never get values in the form you show other than by hardcoding them in the source code:

C:\test>perl -E"my $a = 000.76; my $b = 4; my $c = $a * $b; say $c;" 304

If they had come from an external source, then they would be actual strings, and be handled correctly:

C:\test>perl -E"my $a = '000.76'; my $b = 4; my $c = $a * $b; say $c;" 3.04

I'm not actually sure what is happening in the first case, though I suspect it has something to do with so-called "Version strings" (aka. v-strings) (maybe in combination with octal? And possibly a bug?), but the situation only arises with values hard-coded into the source, not when read from external sources.


With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
"Science is about questioning the status quo. Questioning authority".
In the absence of evidence, opinion is indistinguishable from prejudice.

The start of some sanity?

Replies are listed 'Best First'.
Re^2: Perl with precision (octal)
by tye (Sage) on Feb 29, 2012 at 00:04 UTC

    A start of 0[0-7] means "octal". So 000.76 is simply the same as 000 . 76 which is '076' which becomes just 76 when used as a number.

    - tye        

      So what you are saying is that the first part is octal zero and the dot is the concatenation operator?
Re^2: Perl with precision
by Marshall (Canon) on Feb 29, 2012 at 00:28 UTC
    This is truly bizarre but I was able to confirm this on my installation.
    I'd never added extraneous leading zero'es in a constant before.
    #!/usr/bin/perl -w use strict; #tested on Active State 10.1 for Windows my $a = 000.76; #note: 0.76 works ok # "000.76" works ok # 00.76 fails # 000.76 fails my $b = 4; my $c = $a * $b; print "$c\n"; #304 not 3.04!! WHOA my $x = 000.76; print "$x\n"; #prints 076 $x = 000.76; $x +=0; print "$x\n"; #prints 76 my $y=0.76; print "$y\n"; #prints 0.76

      See Re^2: Perl with precision (octal). 000.76 is interpreted as 000 . 76 where 000 is treated as octal and becomes just 0.

      Concatenation makes both sides strings so you end up with '0' . '76', which when multiplied becomes numeric as just 76 ...


      With the rise and rise of 'Social' network sites: 'Computers are making people easier to use everyday'
      Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
      "Science is about questioning the status quo. Questioning authority".
      In the absence of evidence, opinion is indistinguishable from prejudice.

      The start of some sanity?

        Thankyou everyone for your responses. I have looked at the various Math packages and will consider using them where appropriate. The question was more directed to the behaviour of the apparent concatenation and in the simplest case how best to treat a string that is formatted as such. It would appear sprintf to remove any leading 0's seems like the safest bet prior to attempting to perform any basic math. Thanks again!
        Thanks this makes sense now! A trap for the unwary, but never-the-less logical and consistent.