Search code examples
stringrakuzerodivide

Raku: Attempt to divide by zero when coercing Rational to Str


I am crunching large amounts of data without a hitch until I added more data. The results are written to file as strings, but I received this error message and I am unable to find programming error after combing my codes for 2 days; my codes have been working fine before new data were added.

Died with the exception:
    Attempt to divide by zero when coercing Rational to Str
      in sub analyzeData at /home/xyz/numberCrunch.p6 line 2720
      in block  at /home/xyz/numberCrunch.p6 line 3363

Segmentation fault (core dumped)

The line 2720 is the line that outputs to file: $fh.say("$result");

So, Rational appears to be a delayed evaluation. Is there a way to force immediate conversion of Rational to decimals? Or make Rational smarter by enabling it to detect 0 denominators early?


Solution

  • First of all: a Rat with a denominator of 0 is a perfectly legal Rational value. So creating a Rat with a 0 denominator will not throw an exception on creation.

    I see two issues really:

    • how do you represent a Rat with a denominator of 0 as a string?
    • how do you want your program to react to such a Rat?

    When you represent a Rats as a string, there is a good chance you will lose precision:

    say 1/3;  # 0.333333
    

    So the problem with Rat to string conversion is more general. Fortunately, there's the .raku method that will not throw:

    say (1/3).raku;   # <1/3>
    say (42/0).raku;  # <42/0>
    

    Now, if you want your program to just not print the value to the file handle if the denominator is 0, then you have several options:

    • prefix with try
    try $fh.say($result)
    
    • check for 0 denominator explicitly
    $fh.say($result) if $result.denominator
    

    Finally, the final error message: "Segmentation fault (core dumped)" is a bit worrying. If this is not a multi-threaded program, we should probably try to find out why that is happening: an execution error should not create a segfault. If it is, then maybe we need to look at your code closer to find out if there are any race conditions on structures such as arrays and hashes.