# Numeric Types¶

## Built-in numeric types¶

There are three numeric types: plain integers (also called integers), long integers, floating point numbers.

Attention

Complex numbers are not supported as built-in types in RPython. However, you can use RPython libraries to handle complex numbers.

This table describes the details of RPython’s built-in types: low-level (LL) types, corresponding C types and sizes in memory (64-bit).

Type

LL Type

C Type

Size (32-bit)

Size (64-bit)

`int`

Signed

long

32

64

`long`

Signed

long

32

64

`float`

Float

double

64

64

For more primitive types, you can find them in the primitive type cheat sheet section.

Note that the `int` type and `long` type are same type in RPython, which have same low level representation and size.

All built-in numeric types support the following operations.

```def numeric(x, y, f, l):
print "int: -1024 =", x
print "float: 3.14 =", f
print "long: 1L =", l

print "x + y =", x + y      # sum of x and y
print "x - y =", x - y      # difference of x and y
print "x * y =", x * y      # product of x and y
print "x / y =", x / y      # quotient of x and y
print "x // y =", x // y    # (floored) quotient of x and y
print "x % y =", x % y      # remainder of x / y
print "-x =", -x            # x negated
print "+x =", +x            # x unchanged

print "abs(x) =", abs(x)              # absolute value or magnitude of x
print "int(x) =", int(f)              # x converted to integer
print "float(x) =", float(y)          # x converted to floating point
# print "divmod(x, y) =", divmod(x, y)  # the pair (x // y, x % y)
# print "pow(x, y) =", pow(x, y)        # x to the power y

def entry_point(argv):
x = -1024    # plain integer
y = 42
f = 3.14     # float
l = 1L       # a long integer
numeric(x, y, f, l)
return 0

def target(*args): return entry_point
if __name__ == "__main__": import sys; entry_point(sys.argv)
```

Attention

Some operations or built-in functions can be used in Python but currently not supported in RPython such as `long()`, `complex()`, `conjugate()`, `x ** y`, `divmode(x, y)`, `pow(x, y)` and `float(nan)`. However, RPython’s math library provided some mathematical functions.

Also, it’s worth noting that RPython do constant folding at the compilation time. Therefore, you may found that some built-in functions work with RPython’s code in some scenarios. For example, you can write `pow(123, 456)` in RPython code and the compiler will calculate the value at the compilation time.

The code snippet shows that although RPython does not support above mentioned built-in functions, it still can do constant folding. For instance, `divmod(x, y)` will not yield any compilation error if x and y are constants.

```def numeric_constfold():
"""Constant folding on numeric."""
x = -1024
y = 42

j = 1j       # yield an imaginary number (complex number with zero real part)
print "complex: 1j =", j
print "divmod(x, y) =", divmod(x, y)  # the pair (x // y, x % y)
print "pow(x, y) =", pow(x, y)        # x to the power y

def numeric_no_constfold(x, y):
"""RPython cannot do constant folding on x and y"""
print "divmod(x, y) =", divmod(x, y)  # the pair (x // y, x % y)
print "pow(x, y) =", pow(x, y)        # x to the power y

def entry_point(argv):
numeric_constfold()
# numeric_no_constfold(int(argv), int(argv))    # compilation error, comment this function to try constant folding
return 0

def target(*args): return entry_point
if __name__ == "__main__": import sys; entry_point(sys.argv)
```

In addition to above functions, the following code illustrated some other unsupported operations in RPython but supported in CPython.

```################### UNSUPPORTED IN RPYTHON ######################

def numeric_unsupported():
"""Operations and functions supported in Python but not supported in RPython."""
x = -1024
y = 42

print "long(x) =", long(x)    # x converted to long integer

re = 1
im = 2
# a complex number with real part re, imaginary part im. im defaults to zero.
print "complex(x) =", complex(re, im)

c = 0
# conjugate of the complex number c. (Identity on real numbers)
print "c.conjugate() =", c.conjugate()

print "x ** y =", x ** y     # x to the power y

# float also accepts the strings "nan" and "inf" with an optional prefix
# "+" or "-" for Not a Number (NaN) and positive or negative infinity.
print "float(inf) =", float("inf")
print "float(+inf) =", float("+inf")
print "float(-inf) =", float("-inf")

print "float(nan) =", float("nan")
print "float(+nan) =", float("+nan")
print "float(-nan) =", float("-nan")

def entry_point(argv):
numeric_unsupported()
return 0

def target(*args): return entry_point
if __name__ == "__main__": import sys; entry_point(sys.argv)
```

Attention

Besides these three built-in numeric types, RPython provides more types such as `r_uint`, `r_int32`, `r_longlong`, etc in the arithmetic module. For more information, please refer to rarithmetic in the rlib section

Not like Python, RPython will not automatically use big integer when appropriate. The big integer type and corresponding operations are provided in the `rbigint` library, please refer to rbigint in the rlib section.

## Bitwise operations¶

Bitwise operations on integer types in RPython are same as Python.

```def numeric_bitwise():
x = 2
y = 4
n = 1

print "x = ", x, ", y = ", y
# the bitwise operations sorted in ascending priority
print "x | y =", x | y      # bitwise or of x and y
print "x ^ y =", x ^ y      # bitwise exclusive or of x and y
print "x & y =", x & y      # bitwise and of x and y
print "x << n =", x << n    # x shifted left by n bits
print "x >> n =", x >> n    # x shifted right by n bits
print "~x =", ~x            # the bits of x inverted

def entry_point(argv):
numeric_bitwise()
return 0

def target(*args): return entry_point
if __name__ == "__main__": import sys; entry_point(sys.argv)
```

## Additional methods¶

In Python, there are several additional methods on integer and float types. However, all these methods are not supported in RPython. For example, `int.bit_length()` and `long.bit_length()` can be used to get the number of bits to present an integer. Others like `float.as_integer_ratio()`, `float.is_integer()`, `float.hex()`, and `float.fronhex(S)` are also not supported.

Attention

All additional methods such as `int.bit_length()` and `float.float.as_integer_ratio()` on numeric types are not supported in RPython.

## Math functions¶

In Python, the `math` module provides access to the mathematical functions defined by the C standard. For RPython, you can call math functions in the similar way.

The math functions contain `fabs`, `log`, `log10`, `log1p`, `copysign`, `atan2`, `frexp`, `modf`, `ldexp`, `pow`, `fmod`, `hypot`, `floor`, `sqrt`, `sin`, `cos`, `acos`, `asin`, `atan`, `ceil`, `cosh`, `exp`, `fabs`, `sinh`, `tan`, `tanh`, `acosh`, `asinh`, `atanh`, `expm1`. These math functions will call corresponding C functions in libc.

```import math

def numeric_math():
print math.exp(1e-5) - 1
print math.pi
print math.log(10)
print math.floor(1.5)
print math.sqrt(2)

def entry_point(argv):
numeric_math()
return 0

def target(*args): return entry_point
if __name__ == "__main__": import sys; entry_point(sys.argv)
```