[erlang-questions] math:pow(X, Y).

Richard O'Keefe ok@REDACTED
Tue Mar 20 02:35:02 CET 2012


On 20/03/2012, at 6:17 AM, Yves S. Garret wrote:

> Hi all,
> 
>    That's the standard method that I use to raise a value to a power.  I compared this to the way Python does raising to a power and this is the result that I get:
> 
> Erlang:
> 11> math:pow(42, 909).
> ** exception error: bad argument in an arithmetic expression
>      in function  math:pow/2
>         called as math:pow(42,909)
> 
> Python:
> http://bin.cakephp.org/view/1006418268
> 
> Now.  Why is it in Erlang's case I get a float as a return value?

Because you explicitly called something that is *defined* to return
floating point values.  Basically, the math: module consists of
wrappers around the C <math.h> library.  math:pow(1, 1) => 1.0
because math:pow/2 is something you call when you *want* a floating
point result.

>  Is there a method that only returns a long?

What's a "long"?

-module(rtp).
-export([rtp/2]).

%% rtp(Base, Power) returns Base ** Power.
%% The answer has the same type as Base.
%% If Base is an integer, Power must be non-negative.

-spec rtp(integer(), integer()) -> integer()
    ;    (float(),   integer()) -> float().

rtp(Base, Power)
  when is_integer(Base), is_integer(Power), Power >= 0 ->
    rtpi(Base, Power, 1);
rtp(Base, Power)
  when is_float(Base), is_integer(Power), Power >= 0 ->
    rtpf(Base, Power, 1.0);
rtp(Base, Power)
  when is_float(Base), is_integer(Power), Power < 0 ->
    1.0 / rtpf(Base, -Power, 1.0).

-spec rtpi(integer(), integer(), integer()) -> integer().

rtpi(Base, Power, R) when Power > 2 ->
    rtpi(Base * Base, Power bsr 1,
        case Power band 1
          of 0 -> R
           ; 1 -> R*Base
        end);
rtpi(Base, 2, R) -> R * (Base * Base);
rtpi(Base, 1, R) -> R * Base;
rtpi(   _, 0, R) -> R.

-spec rtpf(float(), integer(), float()) -> float().

rtpf(Base, Power, R) when Power > 2 ->
    rtpf(Base * Base, Power bsr 1,
        case Power band 1
          of 0 -> R
           ; 1 -> R*Base
        end);
rtpf(Base, 2, R) -> R * (Base * Base);
rtpf(Base, 1, R) -> R * Base;
rtpf(   _, 0, R) -> R.





More information about the erlang-questions mailing list