Standard Library
class float
A 64-bit IEEE 754 floating-point number (binary64).
since 0.1.0-alpha.1linuxwindowswasm
Overview
A literal with a decimal point (2.0) is a float. A float prints with six digits after the decimal point, and the special values print as nan, inf and -inf. Arithmetic follows IEEE 754: an operation such as the square root of a negative number produces nan, and an overflow produces inf, instead of throwing. Use isNaN and isInfinite to test for them; a comparison such as x == float::NaN is never true.
Mixed arithmetic is promoted: an int combined with a float gives a float. To go back to an int call toInt, which truncates. The narrower formats float8, float16 and float32 are reached with toFloat8, toFloat16 and toFloat32.
Description
float is an IEEE 754 binary64 number and the type of any literal with a decimal point. It is a value type. There is no exponent notation in literals: write 1000.0, not 1e3.
A float always prints with six digits after the point. Infinities print as inf and -inf, negative zero as -0.000000, and every NaN prints as nan, whatever its internal bits.
Rounding, printing and special values
float x = 3.5;
console.writeln(x);
console.writeln(x.floor());
console.writeln(x.ceil());
console.writeln(x.round());
console.writeln((-2.5).round());
console.writeln(x.trunc());
console.writeln((-3.99).toInt());
console.writeln(2.0.sqrt());
console.writeln((-1.0).sqrt());
console.writeln(0.1 + 0.2 == 0.3);
console.writeln(0.1 + 0.2);
console.writeln(1000000.0 * 1000000.0);
float zero = 0.0;
console.writeln(1.0 / zero);
console.writeln(-1.0 / zero);
console.writeln(zero / zero);
console.writeln(-zero);
try {
console.writeln((1.0 / zero).toInt());
} catch (RuntimeException e) {
console.writeln("caught: ${e.message}");
}
3.500000
3.000000
4.000000
4.000000
-3.000000
3.000000
-3
1.414214
nan
false
0.300000
1000000000000.000000
inf
-inf
nan
-0.000000
caught: float is not finite or out of int64 range for toInt()
Rules
- Arithmetic follows IEEE 754. Division by zero gives infinity (or NaN for
0.0 / 0.0) rather than throwing. round()rounds halves away from zero.sqrt()of a negative number is NaN, not an error.toInt()truncates toward zero. It throws a catchableRuntimeExceptionfor NaN, an infinity or a value outside theintrange.- A bare
==between two floats is the IEEE operator:NaN == NaNisfalse, and-0.0 == 0.0istrue. - Where equality is derived or a value is used as a key, floats compare by the canonical relation instead: every NaN equals every NaN, and
-0.0equals0.0. That relation applies to the==a struct gets automatically, toMapkeys, and tomatcharms.canonEqis the same relation as a method. - A
matcharm can test for NaN withfloat::NaN. - If you write your own
==for a struct, it means exactly what you wrote: floats inside it compare with the IEEE operators. bits()returns the raw 64-bit pattern as anint, andfloat::fromBits(n)builds a float from one. A pattern you construct round-trips exactly. The bits of a NaN produced by arithmetic are not specified.string.toFloat()parses finite decimal numbers only and returnsNonefor anything else, including"inf"and"nan".
Examples
Canonical equality for NaN, in keys, structs and match:
IEEE equality versus the canonical relation
struct Reading {
float v = 0.0;
}
void classify(float f) {
match (f) {
float::NaN => console.writeln("not a number");
else => console.writeln("a number");
}
}
float zero = 0.0;
float nan = zero / zero;
Reading a = Reading(nan);
Reading b = Reading(nan);
console.writeln(nan == nan);
console.writeln(a == b);
console.writeln(zero == -zero);
console.writeln(nan.canonEq(nan));
Map<float, int> m = Map();
m[nan] = 1;
m[nan] = 2;
console.writeln(m.length());
classify(nan);
classify(1.5);
false
true
true
true
1
not a number
a number
Notes
The narrow formats float8, float16 and float32 are described in lang.sized-floats.
Examples
Typical use
float price = 19.99;
float total = price * 3.0;
console.writeln(total);
console.writeln(total.round());
console.writeln(total.toInt());
console.writeln((0.0 - total).abs());
float bad = (0.0 - 1.0).sqrt();
console.writeln(bad.isNaN());
console.writeln("total: ${total}");
59.970000
60.000000
59
59.970000
true
total: 59.970000
Methods
abs
abs() -> floatThe absolute value: this with any minus sign removed.
A NaN stays a NaN.
Returns
this if it is zero or positive, otherwise its negation.
Examples
console.writeln((0.0 - 3.7).abs());
console.writeln(3.7.abs());
console.writeln(float::NaN.abs().isNaN());
3.700000
3.700000
true
bits
bits() -> intThe raw IEEE 754 binary64 bit pattern, as an int.
Useful for serialization and for inspecting a value exactly. float::fromBits is the inverse. The bits of a NaN produced by arithmetic (rather than written as float::NaN) are not specified and can differ between engines and targets, so do not compare them.
Returns
The 64 bits of this, reinterpreted as a signed int.
Examples
console.writeln(1.0.bits());
console.writeln(1.0.bits().toHex());
console.writeln(float::fromBits(4611686018427387904));
console.writeln(float::fromBits(1.5.bits()) == 1.5);
4607182418800017408
3ff0000000000000
2.000000
true
See also: canonEq
canonEq
canonEq(float other) -> boolCompare two floats under the canonical relation used for struct equality, Map keys and match.
The ordinary == is the IEEE comparison, where NaN is not equal to itself and -0.0 equals 0.0. Under canonEq every NaN equals every other NaN, while -0.0 still equals 0.0. This is also how a struct with a float field decides whether two values are equal.
Parameters
- other
- The value to compare with.
Returns
true if the two values are the same under the canonical relation.
Examples
float nan = float::NaN;
console.writeln(nan == nan);
console.writeln(nan.canonEq(nan));
console.writeln(1.5.canonEq(1.5));
console.writeln(1.5.canonEq(2.5));
false
true
true
false
See also: isNaN
ceil
ceil() -> floatRound up to the nearest whole number that is not less than this.
The result is still a float. Negative numbers round toward zero (-2.5 becomes -2.0).
Returns
The smallest whole-valued float greater than or equal to this.
Examples
console.writeln(2.1.ceil());
console.writeln((0.0 - 2.9).ceil());
console.writeln(5.0.ceil());
3.000000
-2.000000
5.000000
floor
floor() -> floatRound down to the nearest whole number that is not greater than this.
The result is still a float; call toInt to get an int. Negative numbers round away from zero (-2.5 becomes -3.0).
Returns
The largest whole-valued float less than or equal to this.
Examples
console.writeln(2.9.floor());
console.writeln((0.0 - 2.1).floor());
console.writeln(5.0.floor());
2.000000
-3.000000
5.000000
isInfinite
isInfinite() -> boolTest whether the value is positive or negative infinity.
Infinity results from overflow, for example 10.0.pow(400.0). A NaN is not infinite.
Returns
true if this is inf or -inf.
Examples
float big = 10.0.pow(400.0);
console.writeln(big);
console.writeln(big.isInfinite());
console.writeln((0.0 - big).isInfinite());
console.writeln(1.0.isInfinite());
console.writeln(float::NaN.isInfinite());
inf
true
true
false
false
See also: isNaN
isNaN
isNaN() -> boolTest whether the value is NaN ("not a number").
NaN results from operations such as the square root of a negative number. It is the only value that is not equal to itself, which is why x == float::NaN is useless and isNaN exists.
Returns
true if this is NaN.
Examples
float r = (0.0 - 1.0).sqrt();
console.writeln(r.isNaN());
console.writeln(r == r);
console.writeln(1.0.isNaN());
true
false
false
See also: isInfinite, canonEq
pow
pow(float e) -> floatRaise this to a power.
Follows the C pow function: a result too large to represent is inf, and a negative base with a fractional exponent is NaN.
Parameters
- e
- The exponent.
Returns
this raised to the power e.
Examples
console.writeln(2.0.pow(10.0));
console.writeln(9.0.pow(0.5));
console.writeln(2.0.pow(0.0 - 1.0));
console.writeln(10.0.pow(400.0));
1024.000000
3.000000
0.500000
inf
See also: sqrt
round
round() -> floatRound to the nearest whole number, with halves rounded away from zero.
2.5 becomes 3.0 and -2.5 becomes -3.0, as in the C round function; this is not banker's rounding. The result is still a float.
Returns
The nearest whole-valued float.
Examples
console.writeln(2.4.round());
console.writeln(2.5.round());
console.writeln((0.0 - 2.5).round());
console.writeln(3.5.round());
2.000000
3.000000
-3.000000
4.000000
sqrt
sqrt() -> floatThe square root.
A negative number gives NaN rather than throwing; test the result with isNaN.
Returns
The non-negative square root of this, or NaN if this is negative.
Examples
console.writeln(16.0.sqrt());
console.writeln(2.0.sqrt());
float r = (0.0 - 4.0).sqrt();
console.writeln(r.isNaN());
4.000000
1.414214
true
See also: pow
toFloat16
toFloat16() -> float16Convert to the 16-bit float16 format (IEEE binary16).
The value is rounded to the nearest representable one, ties to even. The conversion throws when a finite value is too large for the format (the largest finite float16 is 65504); an infinity converts to an infinity and a NaN to the NaN.
Returns
The nearest float16.
Throws
RuntimeException- when
thisis finite but outside the range offloat16.
Examples
float16 a = 0.1.toFloat16();
console.writeln(a.toFloat());
try {
console.writeln(70000.0.toFloat16());
} catch (RuntimeException e) {
console.writeln("caught: ${e.message}");
}
0.099976
caught: toFloat16: value out of range (max finite 65504)
See also: float16, toFloat8, toFloat32
toFloat32
toFloat32() -> float32Convert to the 32-bit float32 format (IEEE binary32).
The value is rounded to the nearest representable one, ties to even, so precision beyond about seven decimal digits is lost. The conversion throws when a finite value is too large for the format (the largest finite float32 is about 3.4e38).
Returns
The nearest float32.
Throws
RuntimeException- when
thisis finite but outside the range offloat32.
Examples
float32 a = 0.1.toFloat32();
console.writeln(a.toFloat());
console.writeln(a.toFloat() == 0.1);
console.writeln(a.toFloat().bits() == 0.1.bits());
0.100000
false
false
See also: float32, toFloat8, toFloat16
toFloat8
toFloat8() -> float8Convert to the 8-bit float8 format (E4M3).
The value is rounded to the nearest representable one, ties to even. The conversion throws instead of overflowing: float8 has no infinity, so a value beyond its finite range cannot be represented. A NaN converts to the float8 NaN.
Returns
The nearest float8.
Throws
RuntimeException- when
thisis infinite or finite but too large forfloat8(the largest finite value is 448).
Examples
float8 a = 1.5.toFloat8();
console.writeln(a.toFloat());
try {
console.writeln(1000.0.toFloat8());
} catch (RuntimeException e) {
console.writeln("caught: ${e.message}");
}
1.500000
caught: toFloat8: value out of range (max finite 448)
See also: float8, toFloat16, toFloat32
toInt
toInt() -> intConvert to an int by dropping the fractional part (rounding toward zero).
Throws instead of returning a wrong number when there is no int to return.
Returns
The truncated value as an int.
Throws
RuntimeException- when
thisis NaN, infinite, or outside the range of a 64-bitint.
Examples
console.writeln(3.99.toInt());
console.writeln((0.0 - 3.99).toInt());
console.writeln(2.5.round().toInt());
try {
console.writeln(float::NaN.toInt());
} catch (RuntimeException e) {
console.writeln("caught: ${e.message}");
}
3
-3
3
caught: float is not finite or out of int64 range for toInt()
toString
toString() -> stringFormat the number as text, with six digits after the decimal point.
The result is also what string concatenation and ${} interpolation produce. A NaN is always spelled nan, and the infinities inf and -inf. Negative zero prints as -0.000000.
Returns
The decimal text of this.
Examples
console.writeln(3.5.toString());
console.writeln(0.1 + 0.2);
console.writeln(float::NaN.toString());
console.writeln((0.0 - 1.0).sqrt().toString());
string s = "value=" + 2.0.toString();
console.writeln(s);
3.500000
0.300000
nan
nan
value=2.000000
trunc
trunc() -> floatDrop the fractional part, rounding toward zero.
Unlike floor, a negative number is not rounded down: -3.99 becomes -3.0. The result is still a float; use toInt for an int.
Returns
this without its fractional part.
Examples
console.writeln(3.99.trunc());
console.writeln((0.0 - 3.99).trunc());
console.writeln((0.0 - 3.99).floor());
3.000000
-3.000000
-4.000000
See also: floor, ceil, round, toInt
See also
- int — The signed 64-bit integer type, the default type of whole numbers.
- Sized floats: float8, float16, float32 — The narrow floating-point formats, how every operation re-rounds, and where they overflow or throw.
- Numeric conversions and working types — How operands of different numeric types combine, and when a value is converted on its way into a typed variable, field, parameter or return.