Integer-Valued Basic Functions
This chapter describes Stan’s built-in function that take various types of arguments and return integer values.
Integer-valued arithmetic operators
Stan’s arithmetic is based on standard double-precision C++ integer and floating-point arithmetic. If the arguments to an arithmetic operator are both integers, as in 2 + 2
, integer arithmetic is used. If one argument is an integer and the other a floating-point value, as in 2.0 + 2
and 2 + 2.0
, then the integer is promoted to a floating point value and floating-point arithmetic is used.
Integer arithmetic behaves slightly differently than floating point arithmetic. The first difference is how overflow is treated. If the sum or product of two integers overflows the maximum integer representable, the result is an undesirable wraparound behavior at the bit level. If the integers were first promoted to real numbers, they would not overflow a floating-point representation. There are no extra checks in Stan to flag overflows, so it is up to the user to make sure it does not occur.
Secondly, because the set of integers is not closed under division and there is no special infinite value for integers, integer division implicitly rounds the result. If both arguments are positive, the result is rounded down. For example, 1 / 2
evaluates to 0 and 5 / 3
evaluates to 1.
If one of the integer arguments to division is negative, the latest C++ specification ( C++11), requires rounding toward zero. This would have 1 / 2
and -1 / 2
evaluate to 0, -7 / 2
evaluate to -3, and 7 / 2
evaluate to 3. Before the C++11 specification, the behavior was platform dependent, allowing rounding up or down. All compilers recent enough to be able to deal with Stan’s templating should follow the C++11 specification, but it may be worth testing if you are not sure and plan to use integer division with negative values.
Unlike floating point division, where 1.0 / 0.0
produces the special positive infinite value, integer division by zero, as in 1 / 0
, has undefined behavior in the C++ standard. For example, the clang++ compiler on Mac OS X returns 3764, whereas the g++ compiler throws an exception and aborts the program with a warning. As with overflow, it is up to the user to make sure integer divide-by-zero does not occur.
Binary infix operators
Operators are described using the C++ syntax. For instance, the binary operator of addition, written X + Y
, would have the Stan signature int operator+(int, int)
indicating it takes two real arguments and returns a real value. As noted previously, the value of integer division is platform-dependent when rounding is platform dependent before C++11; the descriptions below provide the C++11 definition.
int
operator+
(int x, int y)
The sum of the addends x and y \[\begin{equation*} \text{operator+}(x,y) = (x + y) \end{equation*}\]
int
operator-
(int x, int y)
The difference between the minuend x and subtrahend y \[\begin{equation*}
\text{operator-}(x,y) = (x - y) \end{equation*}\]
int
operator*
(int x, int y)
The product of the factors x and y \[\begin{equation*} \text{operator*}(x,y) = (x
\times y) \end{equation*}\]
int
operator/
(int x, int y)
The integer quotient of the dividend x and divisor y \[\begin{equation*}
\text{operator/}(x,y) = \begin{cases} \lfloor x / y \rfloor & \text{if
} x / y \geq 0 \\ - \lfloor \text{floor}(-x / y) \rfloor & \text{if }
x / y < 0. \end{cases} \end{equation*}\] deprecated; - use operator%/%
instead.
int
operator%/%
(int x, int y)
The integer quotient of the dividend x and divisor y \[\begin{equation*}
\text{operator\%/\%}(x,y) = \begin{cases} \lfloor x / y \rfloor & \text{if
} x / y \geq 0 \\ - \lfloor \text{floor}(-x / y) \rfloor & \text{if }
x / y < 0. \end{cases} \end{equation*}\]
int
operator%
(int x, int y)
x modulo y, which is the positive remainder after dividing x by y. If both x and y are non-negative, so is the result; otherwise, the sign of the result is platform dependent. \[\begin{equation*} \mathrm{operator\%}(x, y) \ =
\ x \ \text{mod} \ y \ = \ x - y * \lfloor x / y \rfloor \end{equation*}\]
Unary prefix operators
int
operator-
(int x)
The negation of the subtrahend x \[\begin{equation*} \text{operator-}(x) = -x \end{equation*}\]
T
operator-
(T x)
Vectorized version of operator-
. If T x
is a (possibly nested) array of integers, -x
is the same shape array where each individual integer is negated.
int
operator+
(int x)
This is a no-op. \[\begin{equation*} \text{operator+}(x) = x \end{equation*}\]
Absolute functions
T
abs
(T x)
The absolute value of x.
This function works elementwise over containers such as vectors. Given a type T
which is int
, or an array of int
s, abs
returns the same type where each element has had its absolute value taken.
int
int_step
(int x)
int
int_step
(real x)
Return the step function of x as an integer, \[\begin{equation*} \mathrm{int\_step}(x)
= \begin{cases} 1 & \text{if } x > 0 \\ 0 & \text{if } x \leq 0 \text{
or } x \text{ is } NaN \end{cases} \end{equation*}\] Warning: int_step(0)
and int_step(NaN)
return 0 whereas step(0)
and step(NaN)
return 1.
See the warning in section step functions about the dangers of step functions applied to anything other than data.
Available since 2.0Bound functions
int
min
(int x, int y)
Return the minimum of x and y. \[\begin{equation*} \text{min}(x, y) = \begin{cases} x &
\text{if } x < y\\ y & \text{otherwise} \end{cases} \end{equation*}\]
int
max
(int x, int y)
Return the maximum of x and y. \[\begin{equation*} \text{max}(x, y) = \begin{cases} x &
\text{if } x > y\\ y & \text{otherwise} \end{cases} \end{equation*}\]
Size functions
int
size
(int x)
int
size
(real x)
Return the size of x
which for scalar-valued x
is 1
Casting functions
It is possible to cast real numbers to integers as long as the real value is data
. See data only qualifiers in the Stan Reference Manual.
int
to_int
(data real x)
Return the value x
truncated to an integer. This will throw an error if the value of x
is too big to represent as a 32-bit signed integer.
This is similar to trunc
(see Rounding functions) but the return type is of type int
. For example, to_int(3.9)
is 3
, and to_int(-3.9)
is -3
.
I
to_int
(data T x)
The vectorized version of to_int
. This function accepts a (possibly nested) array of reals and returns an array of the same shape where each element has been truncated to an integer.