Computing: Free Pascal Programming

Formatted output of real numbers.


One of the problems, that you encounter, when writing math or scientific applications, is the display of the results. What I mean, is the display of real numbers, having none or several significant decimal digits, and you, in your application not wanting to display them all, but only 2 or 3. Free Pascal provides two real to string conversion functions:


In my Free Pascal applications, I normally use a custom function RFormat to solve these problems. I tried several approaches, working more or less well. Finally, I think to have found the code, that should work fine in all circumstances. The idea is a function, that has as arguments the number to convert and the number of decimal digits to display. It should use scientific notation, if the number is to small to be displayed for the decimal digits given and should use fixed point format (with dropping of the insignificant decimal digits) otherwise. Checking if the number may be correctly displayed is easy: Any number with absolute value greater than 10-n may be correctly shown with n decimal digits. Using FloatToStrF to display the fixed point number is not an option; as said above, this function always displays exactly n decimal digits. If you have a look at the source code of my various applications, you see that I tried several ways to suppress the insignificant decimal digits. And only now, while writing my TimerCircuits555 application, that I realize, that in fact there is a very simple possibility.

The trick consists in rounding the number to the given number of decimal digits and then using the FloatToStr function, that by default, suppresses the non significant zeros. How to do to round a real to n decimal digits? Just multiply it by 10n, use the Round function to convert it to an integer, then divide this integer by 10n.
Example (n = 2): If R = 12.3456 then Round(100 * R) = 1235 and 1235 / 100 = 12.35. And using FloatToStr, this is displayed 12.35 as 1.2 would be displayed as 1.2 and 1 as 1 (and not 1.20 resp. 1.00, as would be with FloatToStrF).

A little problem here: Pascal has no build-in power function. Two possibilities: 1. Including the math unit. 2. Writing our own power function:

    function Power(R: Real; N: Integer): Real;
    var
        I: Integer;
        Pow: Real;
    begin
        Pow := 1;
        for I := 1 to Abs(N) do
            Pow *= R;
        if N < 0 then
            Pow := 1 / Pow;
        Result := Pow;
    end;

And finally, the real number formatting function, as described above:

    function RFormat(R: Real; F: Integer): string;
    var
        R0: Real;
        SR: string;
    begin
        SR := '';
        if R = 0 then
            SR := '0'
        else begin
            if F >= 0 then begin
                R0 := Round(R * Power(10, F)) / Power(10, F);
                if Abs(R0) < Power(10, -F) then
                    SR := FloatToStrF(R, ffExponent, F, 0)
                else
                    SR := FloatToStr(R0);
            end;
        end;
        Result := SR;
    end;
Note that the scientific notation number is actually displayed with one significant digit less than the given function argument and that its insignificant zeros are not dropped. You can improve the function, considering this, if you would like so. I think, it's no big deal, as in most applications, these small numbers are exceptional situations (otherwise you would probably choose a higher value for F) and that what is important is to avoid getting a display of 0 in this case.


If you find this text helpful, please, support me and this website by signing my guestbook.