3.2 Numbers
Numbers in Guide: Racket introduces numbers.
All numbers are complex numbers. Some of them are real numbers, and all of the real numbers that can be represented are also rational numbers, except for +inf.0 (positive infinity), -inf.0 (negative infinity), and +nan.0 (not-a-number). Among the rational numbers, some are integers, because round applied to the number produces the same number.
Orthogonal to those categories, each number is also either an exact number or an inexact number. Unless otherwise specified, computations that involve an inexact number produce inexact results. Certain operations on inexact numbers, however, produce an exact number, such as multiplying an inexact number with an exact 0. Some operations, which can produce an irrational number for rational arguments (e.g., sqrt), may produce inexact results even for exact arguments.
In the case of complex numbers, either the real and imaginary parts are both exact or inexact, or the number has an exact zero real part and an inexact imaginary part; a complex number with an exact zero imaginary part is a real number.
Inexact real numbers are implemented as either single- or double-precision IEEE floating-point numbers – the latter by default, and the former only when support for 32-bit inexact numbers is specifically enabled when the run-time system is built, and when computation starts with numerical constants specified as single-precision numbers.
The precision and size of exact numbers is limited only by available memory (and the precision of operations that can produce irrational numbers). In particular, adding, multiplying, subtracting, and dividing exact numbers always produces an exact result.
Inexact numbers can be coerced to exact form, except for the inexact numbers +inf.0, -inf.0, and +nan.0, which have no exact form. Dividing a number by exact zero raises an exception; dividing a non-zero number other than +nan.0 by an inexact zero returns +inf.0 or -inf.0, depending on the sign of the dividend. The +nan.0 value is not = to itself, but +nan.0 is eqv? to itself. Conversely, (= 0.0 -0.0) is #t, but (eqv? 0.0 -0.0) is #f. The datum -nan.0 refers to the same constant as +nan.0.
Calculations with infinites produce results consistent with IEEE double-precision floating point where IEEE specifies the result; in cases where IEEE provides no specification (e.g., (angle +inf.0+inf.0i)), the result corresponds to the limit approaching infinity, or +nan.0 if no such limit exists.
A fixnum is an exact integer whose two’s complement representation fit into 31 bits on a 32-bit platform or 63 bits on a 64-bit platform; furthermore, no allocation is required when computing with fixnums. See also the racket/fixnum module, below.
Two fixnums that are = are also the same according to eq?. Otherwise, the result of eq? applied to two numbers is undefined.
Two numbers are eqv? when they are both inexact or both exact, and when they are = (except for +nan.0, 0.0, and -0.0, as noted above). Two numbers are equal? when they are eqv?.
3.2.1 Number Types
Examples: |
> (number? 1) |
#t |
> (number? 2+3i) |
#t |
> (number? "hello") |
#f |
Examples: |
> (real? 1) |
#t |
> (real? +inf.0) |
#t |
> (real? 2+3i) |
#f |
> (real? 2.0+0.0i) |
#f |
> (real? "hello") |
#f |
Examples: |
> (rational? 1) |
#t |
> (rational? +inf.0) |
#f |
> (real? "hello") |
#f |
Examples: |
> (integer? 1) |
#t |
> (integer? 2.3) |
#f |
> (integer? 4.0) |
#t |
> (integer? +inf.0) |
#f |
> (integer? 2+3i) |
#f |
> (integer? "hello") |
#f |
(exact-integer? v) → boolean? |
v : any/c |
Examples: |
> (exact-integer? 1) |
#t |
> (exact-integer? 4.0) |
#f |
(exact-nonnegative-integer? v) → boolean? |
v : any/c |
Examples: |
> (exact-nonnegative-integer? 0) |
#t |
> (exact-nonnegative-integer? -1) |
#f |
(exact-positive-integer? v) → boolean? |
v : any/c |
Examples: |
> (exact-positive-integer? 1) |
#t |
> (exact-positive-integer? 0) |
#f |
(inexact-real? v) → boolean? |
v : any/c |
Examples: |
> (zero? 0) |
#t |
> (zero? -0.0) |
#t |
Examples: |
> (positive? 10) |
#t |
> (positive? -10) |
#f |
> (positive? 0.0) |
#f |
Examples: |
> (negative? 10) |
#f |
> (negative? -10) |
#t |
> (negative? -0.0) |
#f |
Examples: |
> (even? 10.0) |
#t |
> (even? 11) |
#f |
> (even? +inf.0) |
even?: expects argument of type <integer>; given +inf.0 |
Examples: |
> (odd? 10.0) |
#f |
> (odd? 11) |
#t |
> (odd? +inf.0) |
odd?: expects argument of type <integer>; given +inf.0 |
Examples: |
> (exact? 1) |
#t |
> (exact? 1.0) |
#f |
Examples: |
> (inexact? 1) |
#f |
> (inexact? 1.0) |
#t |
(inexact->exact z) → exact? |
z : number? |
Examples: |
> (inexact->exact 1) |
1 |
> (inexact->exact 1.0) |
1 |
(exact->inexact z) → inexact? |
z : number? |
Examples: |
> (exact->inexact 1) |
1.0 |
> (exact->inexact 1.0) |
1.0 |
3.2.2 Arithmetic
Examples: |
> (+ 1 2) |
3 |
> (+ 1.0 2+3i 5) |
8.0+3.0i |
> (+) |
0 |
Examples: |
> (- 5 3.0) |
2.0 |
> (- 1) |
-1 |
> (- 2+7i 1 3) |
-2+7i |
Examples: |
> (* 2 3) |
6 |
> (* 8.0 9) |
72.0 |
> (* 1+2i 3+4i) |
-5+10i |
If z is exact 0 and no w is exact 0, then the result is exact 0. If any w is exact 0, the exn:fail:contract:divide-by-zero exception is raised.
Examples: |
> (/ 3 4) |
3/4 |
> (/ 81 3 3) |
9 |
> (/ 10.0) |
0.1 |
> (/ 1+2i 3+4i) |
11/25+2/25i |
Examples: |
> (quotient 10 3) |
3 |
> (quotient -10.0 3) |
-3.0 |
> (quotient +inf.0 3) |
quotient: expects type <integer> as 1st argument, given: |
+inf.0; other arguments were: 3 |
If m is exact 0, the exn:fail:contract:divide-by-zero exception is raised.
Examples: |
> (remainder 10 3) |
1 |
> (remainder -10.0 3) |
-1.0 |
> (remainder 10.0 -3) |
1.0 |
> (remainder -10 -3) |
-1 |
> (remainder +inf.0 3) |
remainder: expects type <integer> as 1st argument, given: |
+inf.0; other arguments were: 3 |
| ||||||||
n : integer? | ||||||||
m : integer? |
Example: |
> (quotient/remainder 10 3) |
3 |
1 |
(abs q) is between 0 (inclusive) and (abs m) (exclusive), and
the difference between q and (- n (* m (quotient n m))) is a multiple of m.
If m is exact 0, the exn:fail:contract:divide-by-zero exception is raised.
Examples: |
> (modulo 10 3) |
1 |
> (modulo -10.0 3) |
2.0 |
> (modulo 10.0 -3) |
-2.0 |
> (modulo -10 -3) |
-1 |
> (modulo +inf.0 3) |
modulo: expects type <integer> as 1st argument, given: |
+inf.0; other arguments were: 3 |
Examples: |
> (abs 1.0) |
1.0 |
> (abs -1) |
1 |
Examples: |
> (max 1 3 2) |
3 |
> (max 1 3 2.0) |
3.0 |
Examples: |
> (min 1 3 2) |
1 |
> (min 1 3 2.0) |
1.0 |
Examples: |
> (gcd 10) |
10 |
> (gcd 12 81.0) |
3.0 |
Examples: |
> (lcm 10) |
10 |
> (lcm 3 4.0) |
12.0 |
Examples: |
> (round 17/4) |
4 |
> (round -17/4) |
-4 |
> (round 2.5) |
2.0 |
> (round -2.5) |
-2.0 |
Examples: |
> (floor 17/4) |
4 |
> (floor -17/4) |
-5 |
> (floor 2.5) |
2.0 |
> (floor -2.5) |
-3.0 |
Examples: |
> (ceiling 17/4) |
5 |
> (ceiling -17/4) |
-4 |
> (ceiling 2.5) |
3.0 |
> (ceiling -2.5) |
-2.0 |
Examples: |
> (truncate 17/4) |
4 |
> (truncate -17/4) |
-4 |
> (truncate 2.5) |
2.0 |
> (truncate -2.5) |
-2.0 |
Examples: |
> (numerator 5) |
5 |
> (numerator 17/4) |
17 |
> (numerator 2.3) |
2589569785738035.0 |
(denominator q) → integer? |
q : rational? |
Examples: |
> (denominator 5) |
1 |
> (denominator 17/4) |
4 |
> (denominator 2.3) |
1125899906842624.0 |
(rationalize x tolerance) → real? |
x : real? |
tolerance : real? |
Examples: |
> (rationalize 1/4 1/10) |
1/3 |
> (rationalize -1/4 1/10) |
-1/3 |
> (rationalize 1/4 1/4) |
0 |
> (rationalize 11/40 1/4) |
1/2 |
3.2.3 Number Comparison
Examples: |
> (= 1 1.0) |
#t |
> (= 1 2) |
#f |
> (= 2+3i 2+3i 2+3i) |
#t |
Examples: |
> (< 1 1) |
#f |
> (< 1 2 3) |
#t |
> (< 1 +inf.0) |
#t |
> (< 1 +nan.0) |
#f |
Examples: |
> (<= 1 1) |
#t |
> (<= 1 2 1) |
#f |
Examples: |
> (> 1 1) |
#f |
> (> 3 2 1) |
#t |
> (> +inf.0 1) |
#t |
> (< +nan.0 1) |
#f |
Examples: |
> (>= 1 1) |
#t |
> (>= 1 2 1) |
#f |
3.2.4 Powers and Roots
Examples: |
> (sqrt 4/9) |
2/3 |
> (sqrt 2) |
1.4142135623730951 |
> (sqrt -1) |
0+1i |
(integer-sqrt n) → complex? |
n : integer? |
Examples: |
> (integer-sqrt 4.0) |
2.0 |
> (integer-sqrt 5) |
2 |
| ||||||||
n : integer? |
Examples: |
> (integer-sqrt/remainder 4.0) |
2.0 |
0.0 |
> (integer-sqrt/remainder 5) |
2 |
1 |
Examples: |
> (expt 2 3) |
8 |
> (expt 4 0.5) |
2.0 |
> (expt +inf.0 0) |
1 |
Examples: |
> (exp 1) |
2.718281828459045 |
> (exp 2+3i) |
-7.315110094901103+1.0427436562359045i |
> (exp 0) |
1 |
Examples: |
> (log (exp 1)) |
1.0 |
> (log 2+3i) |
1.2824746787307684+0.982793723247329i |
> (log 1) |
0 |
3.2.5 Trignometric Functions
Examples: |
> (sin 3.14159) |
2.65358979335273e-06 |
> (sin 1.0+5.0i) |
62.44551846769653+40.0921657779984i |
Examples: |
> (cos 3.14159) |
-0.9999999999964793 |
> (cos 1.0+5.0i) |
40.095806306298826-62.43984868079963i |
Examples: |
> (tan 0.7854) |
1.0000036732118496 |
> (tan 1.0+5.0i) |
8.256719834227411e-05+1.0000377833796008i |
Examples: |
> (asin 0.25) |
0.25268025514207865 |
> (asin 1.0+5.0i) |
0.1937931365549321+2.3309746530493123i |
Examples: |
> (acos 0.25) |
1.318116071652818 |
> (acos 1.0+5.0i) |
1.3770031902399644-2.3309746530493123i |
In the two-argument case, the result is roughly the same as (/ (exact->inexact y) (exact->inexact x)), but the signs of y and x determine the quadrant of the result. Moreover, a suitable angle is returned when y divided by x produces +nan.0 in the case that neither y nor x is +nan.0. Finally, if x is exact 0 and y is an exact positive number, the result is exact 0. If both x and y are exact 0, the exn:fail:contract:divide-by-zero exception is raised.
Examples: |
> (atan 0.5) |
0.4636476090008061 |
> (atan 2 1) |
1.1071487177940904 |
> (atan -2 -1) |
-2.0344439357957027 |
> (atan 1.0+5.0i) |
1.530881333938778+0.19442614214700213i |
> (atan +inf.0 -inf.0) |
2.356194490192345 |
3.2.6 Complex Numbers
(make-rectangular x y) → number? |
x : real? |
y : real? |
Example: |
> (make-rectangular 3 4.0) |
3.0+4.0i |
(make-polar magnitude angle) → number? |
magnitude : real? |
angle : real? |
Examples: |
> (make-polar 10 (* pi 1/2)) |
6.123233995736766e-16+10.0i |
> (make-polar 10 (* pi 1/4)) |
7.0710678118654755+7.071067811865475i |
Examples: |
> (real-part 3+4i) |
3 |
> (real-part 5.0) |
5.0 |
Examples: |
> (imag-part 3+4i) |
4 |
> (imag-part 5.0) |
0 |
> (imag-part 5.0+0.0i) |
0.0 |
Examples: |
> (magnitude -3) |
3 |
> (magnitude 3.0) |
3.0 |
> (magnitude 3+4i) |
5 |
Examples: |
> (angle -3) |
3.141592653589793 |
> (angle 3.0) |
0 |
> (angle 3+4i) |
0.9272952180016122 |
> (angle +inf.0+inf.0i) |
0.7853981633974483 |
3.2.7 Bitwise Operations
(bitwise-ior n ...) → exact-integer? |
n : exact-integer? |
Examples: |
> (bitwise-ior 1 2) |
3 |
> (bitwise-ior -32 1) |
-31 |
(bitwise-and n ...) → exact-integer? |
n : exact-integer? |
Examples: |
> (bitwise-and 1 2) |
0 |
> (bitwise-and -32 -1) |
-32 |
(bitwise-xor n ...) → exact-integer? |
n : exact-integer? |
Examples: |
> (bitwise-xor 1 5) |
4 |
> (bitwise-xor -32 -1) |
31 |
(bitwise-not n) → exact-integer? |
n : exact-integer? |
Examples: |
> (bitwise-not 5) |
-6 |
> (bitwise-not -1) |
0 |
(bitwise-bit-set? n m) → boolean? |
n : exact-integer? |
m : exact-nonnegative-integer? |
This operation is equivalent to (not (zero? (bitwise-and n (arithmetic-shift 1 m)))), but it is faster and runs in constant time when n is positive.
Examples: |
> (bitwise-bit-set? 5 0) |
#t |
> (bitwise-bit-set? 5 2) |
#t |
> (bitwise-bit-set? -5 (expt 2 700)) |
#t |
(bitwise-bit-field n start end) → exact-integer? | ||||||||
n : exact-integer? | ||||||||
start : exact-nonnegative-integer? | ||||||||
|
This operation is equivalent to the computation
(bitwise-and (sub1 (arithmetic-shift 1 (- end start))) |
(arithmetic-shift n (- start))) |
but it runs in constant time when n is positive, start and end are fixnums, and (- end start) is no more than the maximum width of a fixnum.
Each pair of examples below uses the same numbers, showing the result both in binary and as integers.
Examples: |
> (format "~b" (bitwise-bit-field (string->number "1101" 2) 1 1)) |
"0" |
> (bitwise-bit-field 13 1 1) |
0 |
> (format "~b" (bitwise-bit-field (string->number "1101" 2) 1 3)) |
"10" |
> (bitwise-bit-field 13 1 3) |
2 |
> (format "~b" (bitwise-bit-field (string->number "1101" 2) 1 4)) |
"110" |
> (bitwise-bit-field 13 1 4) |
6 |
(arithmetic-shift n m) → exact-integer? |
n : exact-integer? |
m : exact-integer? |
Examples: |
> (arithmetic-shift 1 10) |
1024 |
> (arithmetic-shift 255 -3) |
31 |
(integer-length n) → exact-integer? |
n : exact-integer? |
Examples: |
> (integer-length 8) |
4 |
> (integer-length -8) |
3 |
3.2.8 Random Numbers
(random k [generator]) → exact-nonnegative-integer? | ||||||||||||
k : (integer-in 1 4294967087) | ||||||||||||
| ||||||||||||
(random [generator]) → (and/c real? inexact? (>/c 0) (</c 1)) | ||||||||||||
|
In each case, the number is provided by the given pseudo-random number generator (which defaults to the current one, as produced by current-pseudo-random-generator). The generator maintains an internal state for generating numbers. The random number generator uses a 54-bit version of L’Ecuyer’s MRG32k3a algorithm [L'Ecuyer02].
(random-seed k) → void? |
k : (integer-in 1 (sub1 (expt 2 31))) |
(pseudo-random-generator? v) → boolean? |
v : any/c |
(current-pseudo-random-generator) → pseudo-random-generator? |
(current-pseudo-random-generator generator) → void? |
generator : pseudo-random-generator? |
(pseudo-random-generator->vector generator) → vector? |
generator : pseudo-random-generator? |
(vector->pseudo-random-generator vec) |
→ pseudo-random-generator? |
vec : vector? |
| ||||||||||||||
generator : pseudo-random-generator? | ||||||||||||||
vec : vector? |
3.2.9 Number–String Conversions
(number->string z [radix]) → string? |
z : number? |
radix : (or/c 2 8 10 16) = 10 |
Examples: |
> (number->string 3.0) |
"3.0" |
> (number->string 255 8) |
"377" |
(string->number s [radix]) → (or/c number? #f) |
s : string? |
radix : (integer-in 2 16) = 10 |
Examples: |
> (string->number "3.0+2.5i") |
3.0+2.5i |
> (string->number "hello") |
#f |
> (string->number "111" 7) |
57 |
> (string->number "#b111" 7) |
7 |
(real->decimal-string n [decimal-digits]) → string? |
n : real? |
decimal-digits : exact-nonnegative-integer? = 2 |
Before printing, n is converted to an exact number, multiplied by (expt 10 decimal-digits), rounded, and then divided again by (expt 10 decimal-digits). The result of ths process is an exact number whose decimal representation has no more than decimal-digits digits after the decimal (and it is padded with trailing zeros if necessary).
Examples: |
> (real->decimal-string pi) |
"3.14" |
> (real->decimal-string pi 5) |
"3.14159" |
| |||||||||||||||||||||||||||||||||||
bstr : bytes? | |||||||||||||||||||||||||||||||||||
signed? : any/c | |||||||||||||||||||||||||||||||||||
big-endian? : any/c = (system-big-endian?) | |||||||||||||||||||||||||||||||||||
start : exact-nonnegative-integer? = 0 | |||||||||||||||||||||||||||||||||||
end : exact-nonnegative-integer? = (bytes-length bstr) |
| ||||||||||||||||||||||||||||||||||||||||||
n : exact-integer? | ||||||||||||||||||||||||||||||||||||||||||
size-n : (or/c 2 4 8) | ||||||||||||||||||||||||||||||||||||||||||
signed? : any/c | ||||||||||||||||||||||||||||||||||||||||||
big-endian? : any/c = (system-big-endian?) | ||||||||||||||||||||||||||||||||||||||||||
| ||||||||||||||||||||||||||||||||||||||||||
start : exact-nonnegative-integer? = 0 |
The dest-bstr argument must be a mutable byte string of length size-n. The encoding of n is written into dest-bstr starting at offset start, and dest-bstr is returned as the result.
If n cannot be encoded in a string of the requested size and format, the exn:fail:contract exception is raised. If dest-bstr is not of length size-n, the exn:fail:contract exception is raised.
| ||||||||||||||||
→ (and/c real? inexact?) | ||||||||||||||||
bstr : bytes? | ||||||||||||||||
big-endian? : any/c = (system-big-endian?) | ||||||||||||||||
start : exact-nonnegative-integer? = 0 | ||||||||||||||||
end : exact-nonnegative-integer? = (bytes-length bstr) |
| |||||||||||||||||||||||||||||||||||
x : real? | |||||||||||||||||||||||||||||||||||
size-n : (or/c 4 8) | |||||||||||||||||||||||||||||||||||
big-endian? : any/c = (system-big-endian?) | |||||||||||||||||||||||||||||||||||
| |||||||||||||||||||||||||||||||||||
start : exact-nonnegative-integer? = 0 |
The dest-bstr argument must be a mutable byte string of length size-n. The encoding of n is written into dest-bstr starting with byte start, and dest-bstr is returned as the result.
If dest-bstr is provided and it has less than start plus size-n bytes, the exn:fail:contract exception is raised.
3.2.10 Inexact-Real (Flonum) Operations
(require racket/flonum) |
The racket/flonum library provides operations like fl+ that consume and produce only real inexact numbers, which are also known as flonums. Flonum-specific operations provide can better performance when used consistently, and they are as safe as generic operations like +.
See also Fixnum and Flonum Optimizations in Guide: Racket.
3.2.10.1 Flonum Arithmetic
| |||
| |||
| |||
| |||
|
| |||
| |||
| |||
| |||
| |||
| |||
|
| ||
| ||
| ||
|
| ||
| ||
| ||
| ||
| ||
| ||
| ||
| ||
|
(->fl a) → inexact-real? |
a : exact-integer? |
(fl->exact-integer a) → exact-integer? |
a : inexact-real? |
| ||||
| ||||
|
3.2.10.2 Flonum Vectors
A flvector is like a vector, but it holds only inexact real numbers. This representation can be more compact, and unsafe operations on flvectors (see racket/unsafe/ops) can execute more efficiently than unsafe operations on vectors of inexact reals.
An f64vector as provided by ffi/vector stores the same kinds of values as an flvector, but with extra indirections that make f64vectors more convenient for working with foreign libraries. The lack of indirections make unsafe flvector access more efficient.
Two flvectors are equal? if they have the same length, and if the values in corresponding slots of the flvectors are equal?.
(flvector x ...) → flvector? |
x : inexact-real? |
(make-flvector size [x]) → flvector? |
size : exact-nonnegative-integer? |
x : inexact-real? = 0.0 |
(flvector-length vec) → exact-nonnegative-integer? |
vec : flvector? |
(flvector-ref vec pos) → inexact-real? |
vec : flvector? |
pos : exact-nonnegative-integer? |
(flvector-set! vec pos x) → inexact-real? |
vec : flvector? |
pos : exact-nonnegative-integer? |
x : inexact-real? |
3.2.11 Fixnum Operations
(require racket/fixnum) |
The racket/fixnum library provides operations like fx+ that consume and produce only fixnums. The operations in this library are meant to be safe versions of unsafe operations like unsafe-fx+. These safe operations are generally no faster than using generic primitives like +.
The expected use of the racket/fixnum library is for code where the require of racket/fixnum is replaced with
(require (filtered-in |
(λ (name) (regexp-replace #rx"unsafe-" name "")) |
racket/unsafe/ops)) |
to drop in unsafe versions of the library. Alternately, when encountering crashes with code that uses unsafe fixnum operations, use the racket/fixnum library to help debug the problems.
| |||
| |||
| |||
| |||
| |||
| |||
|
| |||
| |||
| |||
| |||
| |||
|
| |||
| |||
| |||
| |||
| |||
| |||
|
| ||
|
3.2.12 Extra Constants and Functions
Examples: |
> (sgn 10) |
1 |
> (sgn -10.0) |
-1.0 |
> (sgn 0) |
0 |
Examples: |
> (conjugate 1) |
1 |
> (conjugate 3+4i) |
3-4i |
(<= (expt 10 m) |
(inexact->exact r)) |
(< (inexact->exact r) |
(expt 10 (add1 m))) |
Examples: |
> (order-of-magnitude 999) |
2 |
> (order-of-magnitude 1000) |
3 |
> (order-of-magnitude 1/100) |
-2 |
> (order-of-magnitude 1/101) |
-3 |