diff --git a/builtin/char.mbt b/builtin/char.mbt index 93cb4140e..34bd52d0c 100644 --- a/builtin/char.mbt +++ b/builtin/char.mbt @@ -13,6 +13,25 @@ // limitations under the License. ///| +/// Calculates the difference between the Unicode code points of two characters. +/// +/// Parameters: +/// +/// * `self` : The first character whose code point serves as the minuend. +/// * `other` : The second character whose code point serves as the subtrahend. +/// +/// Returns an integer representing the difference between the Unicode code +/// points of the two characters. +/// +/// Example: +/// +/// ```moonbit +/// test "Char::op_sub" { +/// let a = 'b' +/// let b = 'a' +/// inspect!(a - b, content="1") // Unicode point of 'b' (98) minus 'a' (97) +/// } +/// ``` pub fn Char::op_sub(self : Char, that : Char) -> Int { self.to_int() - that.to_int() } diff --git a/builtin/console.mbt b/builtin/console.mbt index a712cf82d..98ace4d6b 100644 --- a/builtin/console.mbt +++ b/builtin/console.mbt @@ -19,11 +19,42 @@ fn println_mono(s : String) -> Unit = "%println" fn any_to_string[T](any : T) -> String = "%any.to_string" ///| +/// Prints any value that implements the `Show` trait to the standard output, +/// followed by a newline. +/// +/// Parameters: +/// +/// * `value` : The value to be printed. Must implement the `Show` trait. +/// +/// Example: +/// +/// ```moonbit skip +/// test "println" { +/// println(42) +/// println("Hello, World!") +/// println([1, 2, 3]) +/// } +/// ``` pub fn println[T : Show](input : T) -> Unit { println_mono(input.to_string()) } ///| +/// Prints a value to the standard output and appends a newline. +/// +/// Parameters: +/// +/// * `input` : The value to be printed. Must implement the `Show` trait. +/// +/// Example: +/// +/// ```moonbit skip +/// test "print" { +/// println(42) +/// println("Hello, World!") +/// } +/// ``` +/// /// @alert deprecated "Use `println` instead" /// @coverage.skip pub fn print[T : Show](input : T) -> Unit { @@ -43,9 +74,51 @@ pub fn dump[T](t : T, name? : String, loc~ : SourceLoc = _) -> T { } ///| +/// Represents an error type used by the `inspect!` function to indicate failures +/// in value inspection. Contains a string message describing the nature of the +/// inspection failure. +/// +/// Returns a type constructor that creates an error type from a string message. +/// +/// Example: +/// +/// ```moonbit +/// test "inspect/failure" { +/// let x : Int = 42 +/// inspect!(x, content="42") // Raises InspectError with detailed failure message +/// } +/// ``` pub(all) type! InspectError String ///| +/// Tests if the string representation of an object matches the expected content. +/// Used primarily in test cases to verify the correctness of `Show` +/// implementations and program outputs. +/// +/// Parameters: +/// +/// * `object` : The object to be inspected. Must implement the `Show` trait. +/// * `content` : The expected string representation of the object. Defaults to +/// an empty string. +/// * `location` : Source code location information for error reporting. +/// Automatically provided by the compiler. +/// * `arguments_location` : Location information for function arguments in +/// source code. Automatically provided by the compiler. +/// +/// Throws an `InspectError` if the actual string representation of the object +/// does not match the expected content. The error message includes detailed +/// information about the mismatch, including source location and both expected +/// and actual values. +/// +/// Example: +/// +/// ```moonbit skip +/// test "inspect/basic" { +/// inspect!(42, content="42") +/// inspect!("hello", content="hello") +/// inspect!([1, 2, 3], content="[1, 2, 3]") +/// } +/// ``` pub fn inspect( obj : &Show, content~ : String = "", @@ -65,7 +138,22 @@ pub fn inspect( } ///| -// Used by test driver +/// Represents an error that occurs during snapshot testing. Contains a string +/// message describing the error. +/// +/// Used internally by the test driver to handle snapshot-related errors. Not +/// intended for direct use by end users. +/// +/// Example: +/// +/// ```moonbit +/// test "SnapshotError" { +/// let err : SnapshotError = SnapshotError("failed to load snapshot") +/// match err { +/// SnapshotError(msg) => assert_eq!(msg, "failed to load snapshot") +/// } +/// } +/// ``` pub(all) type! SnapshotError String test "panic error case of inspect" { diff --git a/builtin/failure.mbt b/builtin/failure.mbt index ff1205fec..58f7b7604 100644 --- a/builtin/failure.mbt +++ b/builtin/failure.mbt @@ -13,9 +13,50 @@ // limitations under the License. ///| +/// Represents a generic test failure type used primarily in test assertions and +/// validations. +/// +/// Since this is a type definition using `type!` syntax, it creates an error +/// type `Failure` that wraps a `String` value containing the failure message. +/// +/// Parameters: +/// +/// * `message` : A string describing the nature of the failure. +/// +/// Example: +/// +/// ```moonbit +/// test "Failure" { +/// let err : Failure = Failure("Test assertion failed") +/// match err { +/// Failure(msg) => inspect!(msg, content="Test assertion failed") +/// } +/// } +/// ``` pub(all) type! Failure String ///| +/// Raises a `Failure` error with a given message and source location. +/// +/// Parameters: +/// +/// * `message` : A string containing the error message to be included in the +/// failure. +/// * `location` : The source code location where the failure occurred. +/// Automatically provided by the compiler when not specified. +/// +/// Returns a value of type `T` wrapped in a `Failure` error type. +/// +/// Throws an error of type `Failure` with a message that includes both the +/// source location and the provided error message. +/// +/// Example: +/// +/// ```moonbit +/// test "panic fail" { +/// fail!("Something went wrong") +/// } +/// ``` pub fn fail[T](msg : String, loc~ : SourceLoc = _) -> T!Failure { raise Failure("FAILED: \{loc} \{msg}") } diff --git a/builtin/fixedarray.mbt b/builtin/fixedarray.mbt index cd8c89d0a..f280fe41e 100644 --- a/builtin/fixedarray.mbt +++ b/builtin/fixedarray.mbt @@ -13,6 +13,27 @@ // limitations under the License. ///| +/// +/// Creates an iterator over the elements of a fixed-size array, providing +/// sequential access to each element. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array to iterate over. +/// +/// Returns an iterator that yields each element of the array in order from first +/// to last. +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::iter" { +/// let arr = FixedArray::make(3, 42) +/// let mut sum = 0 +/// arr.iter().each(fn(x) { sum = sum + x }) +/// inspect!(sum, content="126") +/// } +/// ``` /// @intrinsic %iter.from_array pub fn FixedArray::iter[T](self : FixedArray[T]) -> Iter[T] { Iter::new(fn(yield_) { @@ -26,6 +47,27 @@ pub fn FixedArray::iter[T](self : FixedArray[T]) -> Iter[T] { } ///| +/// Returns an iterator that yields both indices and values from the fixed array. +/// The iterator provides pairs of `(index, value)` where indices start from 0 +/// and increment sequentially. +/// +/// Parameters: +/// +/// * `array` : The fixed array to iterate over. +/// +/// Returns an iterator of type `Iter2[Int, T]` that yields tuples of indices and +/// values from the array. +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::iter2" { +/// let arr = FixedArray::make(3, 10) +/// let mut sum = 0 +/// arr.iter2().each(fn(i, x) { sum = sum + i + x }) +/// inspect!(sum, content="33") // (0 + 10) + (1 + 10) + (2 + 10) = 33 +/// } +/// ``` pub fn FixedArray::iter2[T](self : FixedArray[T]) -> Iter2[Int, T] { Iter2::new(fn(yield_) { for i, v in self { @@ -38,6 +80,23 @@ pub fn FixedArray::iter2[T](self : FixedArray[T]) -> Iter2[Int, T] { } ///| +/// Returns an empty fixed-size array of the specified type. +/// +/// Parameters: +/// +/// * `X` : The type parameter specifying the element type of the array. +/// +/// Returns an empty fixed-size array of type `FixedArray[X]`. +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::default" { +/// let arr : FixedArray[Int] = FixedArray::default() +/// inspect!(arr.length(), content="0") +/// inspect!(arr.is_empty(), content="true") +/// } +/// ``` pub fn FixedArray::default[X]() -> FixedArray[X] { [] } @@ -58,6 +117,34 @@ pub fn FixedArray::fill[T](self : FixedArray[T], value : T) -> Unit { } ///| +/// Compares two fixed arrays lexicographically based on their elements. First +/// compares the lengths of the arrays, then compares elements pairwise until a +/// difference is found or all elements have been compared. +/// +/// Parameters: +/// +/// * `self` : The first fixed array to compare. +/// * `other` : The second fixed array to compare. +/// +/// Returns an integer that indicates the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::compare" { +/// let arr1 = [1, 2, 3] +/// let arr2 = [1, 2, 4] +/// let arr3 = [1, 2] +/// inspect!(arr1.compare(arr2), content="-1") // arr1 < arr2 +/// inspect!(arr2.compare(arr1), content="1") // arr2 > arr1 +/// inspect!(arr1.compare(arr3), content="1") // arr1 > arr3 (longer) +/// inspect!(arr1.compare(arr1), content="0") // arr1 = arr1 +/// } +/// ``` pub fn compare[T : Compare](self : FixedArray[T], other : FixedArray[T]) -> Int { let len_self = self.length() let len_other = other.length() diff --git a/builtin/fixedarray_block.mbt b/builtin/fixedarray_block.mbt index 6af5e22d6..30389deb1 100644 --- a/builtin/fixedarray_block.mbt +++ b/builtin/fixedarray_block.mbt @@ -69,6 +69,40 @@ fn UninitializedArray::unsafe_blit_fixed[T]( } ///| +/// Copies a sequence of elements from the source fixed array to a destination +/// fixed array. The arrays may overlap, in which case the copy is performed in a +/// way that preserves the data. +/// +/// Parameters: +/// +/// * `self` : The source fixed array from which elements will be copied. +/// * `dst` : The destination fixed array where elements will be copied to. +/// * `len` : The number of elements to copy. +/// * `src_offset` : The starting position in the source array. Defaults to 0. +/// * `dst_offset` : The starting position in the destination array. Defaults to +/// 0. +/// +/// Throws a panic if: +/// +/// * `src_offset + len` exceeds the length of the source array +/// * `dst_offset + len` exceeds the length of the destination array +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::blit_to" { +/// let src = FixedArray::make(5, 1) +/// let dst = FixedArray::make(5, 0) +/// src.blit_to(dst, len=3, src_offset=1, dst_offset=2) +/// inspect!(dst, content="[0, 0, 1, 1, 1]") +/// } +/// +/// test "panic FixedArray::blit_to/out_of_bounds" { +/// let src = FixedArray::make(3, 1) +/// let dst = FixedArray::make(3, 0) +/// ignore(src.blit_to(dst, len=4)) // Panics: length out of bounds +/// } +/// ``` pub fn FixedArray::blit_to[A]( self : FixedArray[A], dst : FixedArray[A], diff --git a/builtin/hasher.mbt b/builtin/hasher.mbt index 91a58c4b4..62c5b0894 100644 --- a/builtin/hasher.mbt +++ b/builtin/hasher.mbt @@ -28,38 +28,166 @@ let gPRIME4 = 0x27D4EB2F let gPRIME5 = 0x165667B1 ///| -/// xxhash32 Hasher +/// Represents a hasher that implements the xxHash32 algorithm. The hasher +/// maintains a mutable accumulator that is updated with each value added to the +/// hash computation. +/// +/// This struct provides methods for combining different types of values into a +/// single hash value, making it suitable for implementing hash functions for +/// custom types. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher/basic" { +/// let hasher = Hasher::new() +/// hasher.combine_int(42) +/// hasher.combine_string("hello") +/// inspect!(hasher.finalize(), content="860601284") +/// } +/// ``` struct Hasher { mut acc : Int } ///| +/// Creates a new hasher with an optional seed value. +/// +/// Parameters: +/// +/// * `seed` : An integer value used to initialize the hasher's internal state. +/// Defaults to 0. +/// +/// Returns a new `Hasher` instance initialized with the given seed value. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::new" { +/// let h1 = Hasher::new() // Create a hasher with default seed +/// let h2 = Hasher::new(seed=42) // Create a hasher with custom seed +/// let x = 123 +/// h1.combine(x) +/// h2.combine(x) +/// inspect!(h1.finalize() != h2.finalize(), content="true") // Different seeds produce different hashes +/// } +/// ``` pub fn Hasher::new(seed~ : Int = 0) -> Hasher { { acc: seed + gPRIME5 } } ///| +/// Combines a hashable value with the current state of the hasher. This is +/// typically used to incrementally build a hash value from multiple components. +/// +/// Parameters: +/// +/// * `self` : The hasher instance to update. +/// * `value` : The value to be combined with the current hash state. Must +/// implement the `Hash` trait. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine" { +/// let hasher = Hasher::new() +/// hasher.combine(42) +/// hasher.combine("hello") +/// inspect!(hasher.finalize(), content="860601284") +/// } +/// ``` pub fn Hasher::combine[T : Hash](self : Hasher, value : T) -> Unit { value.hash_combine(self) } ///| +/// Combines the unit value (i.e., `()`) into the hasher's internal state by +/// hashing it as an integer value of 0. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object to combine the unit value into. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_unit" { +/// let hasher = Hasher::new() +/// hasher.combine_unit() +/// inspect!(hasher.finalize(), content="148298089") +/// } +/// ``` pub fn Hasher::combine_unit(self : Hasher) -> Unit { self.combine_int(0) } ///| +/// Combines a boolean value into the current hash state. The boolean value is +/// converted to an integer (1 for true, 0 for false) before being combined with +/// the hash. +/// +/// Parameters: +/// +/// * `self` : The hasher instance to update. +/// * `value` : The boolean value to be combined into the hash state. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_bool" { +/// let hasher = Hasher::new() +/// hasher.combine_bool(true) +/// inspect!(hasher.finalize(), content="-205818221") +/// } +/// ``` pub fn Hasher::combine_bool(self : Hasher, value : Bool) -> Unit { self.combine_int(if value { 1 } else { 0 }) } ///| +/// Combines a 32-bit integer value into the hasher's internal state. The value +/// is processed +/// as a 4-byte sequence, and the internal accumulator is updated accordingly. +/// +/// Parameters: +/// +/// * `self` : The hasher instance to update. +/// * `value` : A 32-bit integer value to be incorporated into the hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_int" { +/// let hasher = Hasher::new() +/// hasher.combine_int(42) +/// inspect!(hasher.finalize(), content="1161967057") +/// } +/// ``` pub fn Hasher::combine_int(self : Hasher, value : Int) -> Unit { self.acc += 4 self.consume4(value) } ///| +/// Combines a 64-bit integer value into the hash state by splitting it into two +/// 32-bit parts and processing them separately. This method is used internally +/// by the hash implementation to incorporate 64-bit integers into the hash +/// computation. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object whose internal state will be updated. +/// * `value` : The 64-bit integer value to be incorporated into the hash state. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_int64" { +/// let hasher = Hasher::new() +/// hasher.combine_int64(42L) +/// inspect!(hasher.finalize(), content="-1962516083") +/// } +/// ``` pub fn Hasher::combine_int64(self : Hasher, value : Int64) -> Unit { self.acc += 8 self.consume4(value.to_int()) @@ -67,31 +195,139 @@ pub fn Hasher::combine_int64(self : Hasher, value : Int64) -> Unit { } ///| +/// Combines an unsigned 32-bit integer into the hasher's internal state by +/// reinterpreting it as a signed integer and incorporating it into the hash +/// computation. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object to update. +/// * `value` : The unsigned 32-bit integer value to be combined into the hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_uint" { +/// let hasher = Hasher::new() +/// hasher.combine_uint(42U) +/// inspect!(hasher.finalize(), content="1161967057") +/// } +/// ``` pub fn Hasher::combine_uint(self : Hasher, value : UInt) -> Unit { self.combine_int(value.reinterpret_as_int()) } ///| +/// Combines a 64-bit unsigned integer into the hasher's internal state. Useful +/// for hashing `UInt64` values as part of a larger composite structure. +/// +/// Parameters: +/// +/// * `self` : The hasher instance to update. +/// * `value` : The 64-bit unsigned integer value to be incorporated into the +/// hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_uint64" { +/// let hasher = Hasher::new() +/// hasher.combine_uint64(42UL) +/// inspect!(hasher.finalize(), content="-1962516083") +/// } +/// ``` pub fn Hasher::combine_uint64(self : Hasher, value : UInt64) -> Unit { self.combine_int64(value.reinterpret_as_int64()) } ///| +/// Combines a double-precision floating-point number into the hasher's internal +/// state by reinterpreting its bits as a 64-bit integer. Maintains consistent +/// hashing behavior regardless of the floating-point value's representation. +/// +/// Parameters: +/// +/// * `hasher` : The hasher to combine the value into. +/// * `value` : The double-precision floating-point number to be combined into +/// the hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_double" { +/// let hasher = Hasher::new() +/// hasher.combine_double(3.14) +/// inspect!(hasher.finalize(), content="-428265677") +/// } +/// ``` pub fn Hasher::combine_double(self : Hasher, value : Double) -> Unit { self.combine_int64(value.reinterpret_as_int64()) } ///| +/// Combines a 32-bit floating-point value into the hasher by reinterpreting its +/// bit pattern as a 32-bit integer. The operation maintains the same hash result +/// regardless of the floating-point value's representation. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object that maintains the internal state of the +/// hashing operation. +/// * `value` : The 32-bit floating-point value to be combined into the hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_float" { +/// let hasher = Hasher::new() +/// hasher.combine_float(3.14) +/// inspect!(hasher.finalize(), content="635116317") // Hash of the bits of 3.14 +/// } +/// ``` pub fn Hasher::combine_float(self : Hasher, value : Float) -> Unit { self.combine_int(value.reinterpret_as_int()) } ///| +/// Combines a byte value into the hash state. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object to update with the byte value. +/// * `byte` : The byte value to be combined into the hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_byte" { +/// let hasher = Hasher::new() +/// hasher.combine_byte(b'\xFF') +/// inspect!(hasher.finalize(), content="1955036104") +/// } +/// ``` pub fn Hasher::combine_byte(self : Hasher, value : Byte) -> Unit { self.consume1(value) } ///| +/// Combines a byte sequence into the hasher's internal state using xxHash32 +/// algorithm. Processes the input bytes in chunks of 4 bytes for efficiency, +/// with remaining bytes processed individually. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object to update with the byte sequence. +/// * `bytes` : The byte sequence to be combined into the hash. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_bytes" { +/// let hasher = Hasher::new() +/// hasher.combine_bytes(b"\xFF\x00\xFF\x00") +/// inspect!(hasher.finalize(), content="-686861102") +/// } +/// ``` pub fn Hasher::combine_bytes(self : Hasher, value : Bytes) -> Unit { let mut remain = value.length() let mut cur = 0 @@ -108,6 +344,23 @@ pub fn Hasher::combine_bytes(self : Hasher, value : Bytes) -> Unit { } ///| +/// Combines a string value into the current hash state by processing each +/// character in the string sequentially. +/// +/// Parameters: +/// +/// * `self` : The hasher object whose state will be updated. +/// * `value` : The string value to be combined into the hash state. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_string" { +/// let hasher = Hasher::new() +/// hasher.combine_string("hello") +/// inspect!(hasher.finalize(), content="-655549713") +/// } +/// ``` pub fn Hasher::combine_string(self : Hasher, value : String) -> Unit { for i = 0; i < value.length(); i = i + 1 { self.combine_int(value[i].to_int()) @@ -115,11 +368,47 @@ pub fn Hasher::combine_string(self : Hasher, value : String) -> Unit { } ///| +/// Combines a character value into the hasher's internal state. The character is +/// first converted to its Unicode code point (as an integer) before being +/// combined. +/// +/// Parameters: +/// +/// * `self` : The hasher instance to update. +/// * `value` : The character value to be combined into the hash state. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::combine_char" { +/// let hasher = Hasher::new() +/// hasher.combine_char('A') +/// inspect!(hasher.finalize(), content="-1625495534") +/// } +/// ``` pub fn Hasher::combine_char(self : Hasher, value : Char) -> Unit { self.combine_int(value.to_int()) } ///| +/// Finalizes the hashing process and returns the computed hash value. Applies an +/// avalanche function to improve the distribution of the hash value. +/// +/// Parameters: +/// +/// * `hasher` : The hasher object containing the accumulated hash state. +/// +/// Returns a 32-bit integer representing the final hash value. +/// +/// Example: +/// +/// ```moonbit +/// test "Hasher::finalize" { +/// let hasher = Hasher::new() +/// hasher.combine_byte(b'\xFF') +/// inspect!(hasher.finalize(), content="1955036104") +/// } +/// ``` pub fn Hasher::finalize(self : Hasher) -> Int { self.avalanche() } @@ -167,12 +456,54 @@ fn endian32(input : Bytes, cur : Int) -> Int { // } ///| +/// Implements the `Hash` trait for `String` type, providing a method to combine +/// a string's hash value with a hasher's state. +/// +/// Parameters: +/// +/// * `self` : The string value to be hashed. +/// * `hasher` : The hasher object that will be updated with the string's hash +/// value. +/// +/// Example: +/// +/// ```moonbit +/// test "String::hash" { +/// let s1 = "hello" +/// let s2 = "hello" +/// let s3 = "world" +/// inspect!(Hash::hash(s1) == Hash::hash(s2), content="true") +/// inspect!(Hash::hash(s1) == Hash::hash(s3), content="false") +/// } +/// ``` pub impl Hash for String with hash_combine(self, hasher) { hasher.combine_string(self) } ///| -// https://github.com/skeeto/hash-prospector +/// Implements the `Hash` trait for integer values using a combination of shifts +/// and multiplications to produce a well-distributed hash value. Based on the +/// hash algorithm from hash-prospector +/// (https://github.com/skeeto/hash-prospector). +/// +/// Parameters: +/// +/// * `integer` : The integer value to be hashed. The value will be reinterpreted +/// as an unsigned integer before hashing to ensure consistent behavior across +/// positive and negative values. +/// +/// Returns a 32-bit hash value derived from the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::hash" { +/// let x = 42 +/// inspect!(Hash::hash(x), content="-1704501356") +/// let y = -42 +/// inspect!(Hash::hash(y), content="1617647962") +/// } +/// ``` pub impl Hash for Int with hash(self) { let self = self.reinterpret_as_uint() let mut x = self ^ (self >> 17) @@ -186,21 +517,97 @@ pub impl Hash for Int with hash(self) { } ///| +/// Implements hash combination for integers by combining the integer value with +/// a hasher. This implementation ensures that integers can be used as keys in +/// hash-based collections like hash maps and hash sets. +/// +/// Parameters: +/// +/// * `self` : The integer value to be hashed. +/// * `hasher` : A `Hasher` object that accumulates the hash value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::hash_combine" { +/// let hasher = Hasher::new() +/// hasher.combine_int(42) +/// inspect!(hasher.finalize(), content="1161967057") +/// } +/// ``` pub impl Hash for Int with hash_combine(self, hasher) { hasher.combine_int(self) } ///| +/// Combines the hash value of an unsigned integer with a hasher object. This is +/// useful when you need to hash a data structure that contains unsigned +/// integers. +/// +/// Parameters: +/// +/// * `value` : The unsigned integer to be combined with the hasher. +/// * `hasher` : The hasher object that will incorporate the hash value of the +/// unsigned integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::hash_combine" { +/// let hasher = Hasher::new() +/// hasher.combine_uint(42U) +/// inspect!(hasher.finalize(), content="1161967057") +/// } +/// ``` pub impl Hash for UInt with hash_combine(self, hasher) { hasher.combine_uint(self) } ///| +/// Implements the `Hash` trait for `UInt64` by combining the hash value of an +/// unsigned 64-bit integer into a hasher. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer value to be hashed. +/// * `hasher` : The hasher object used to compute the combined hash value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::hash_combine" { +/// let hasher = Hasher::new() +/// hasher.combine_uint64(42UL) +/// inspect!(hasher.finalize(), content="-1962516083") +/// } +/// ``` pub impl Hash for UInt64 with hash_combine(self, hasher) { hasher.combine_uint64(self) } ///| +/// Implements the `Hash` trait for `Option` types, allowing them to be used as +/// keys in hash-based collections. +/// +/// Parameters: +/// +/// * `self` : The `Option` value to be hashed. +/// * `hasher` : The hasher object that accumulates the hash state. +/// +/// Example: +/// +/// ```moonbit +/// test "Option::hash_combine" { +/// let hasher = Hasher::new() +/// let some_value : Int? = Some(42) +/// let none_value : Int? = None +/// hasher.combine(some_value) +/// inspect!(hasher.finalize(), content="2103260413") +/// let hasher2 = Hasher::new() +/// hasher2.combine(none_value) +/// inspect!(hasher2.finalize(), content="148298089") +/// } +/// ``` pub impl[X : Hash] Hash for X? with hash_combine(self, hasher) { match self { None => hasher.combine_int(0) @@ -209,6 +616,28 @@ pub impl[X : Hash] Hash for X? with hash_combine(self, hasher) { } ///| +/// Implements the `Hash` trait for `Result` type, allowing `Result` values to be +/// used in hash-based collections. +/// +/// Parameters: +/// +/// * `self` : The `Result` value to be hashed. +/// * `hasher` : The hasher object to which the hash value will be combined. +/// +/// Example: +/// +/// ```moonbit +/// test "Result::hash_combine" { +/// let hasher = Hasher::new() +/// let ok_result : Result[Int, String] = Ok(42) +/// let err_result : Result[Int, String] = Err("error") +/// hasher.combine(ok_result) +/// inspect!(hasher.finalize(), content="-1948635851") +/// let hasher = Hasher::new() +/// hasher.combine(err_result) +/// inspect!(hasher.finalize(), content="1953766574") +/// } +/// ``` pub impl[T : Hash, E : Hash] Hash for Result[T, E] with hash_combine( self, hasher diff --git a/builtin/int64_nonjs.mbt b/builtin/int64_nonjs.mbt index 34a24e672..55e2380f4 100644 --- a/builtin/int64_nonjs.mbt +++ b/builtin/int64_nonjs.mbt @@ -13,234 +13,1675 @@ // limitations under the License. ///| +/// Performs unary negation on a 64-bit signed integer, returning its arithmetic +/// inverse. +/// +/// Parameters: +/// +/// * `value` : The 64-bit signed integer to negate. +/// +/// Returns the arithmetic negation of the input value. For all inputs except +/// `Int64::min_value()`, returns the value with opposite sign. When the input is +/// `Int64::min_value()`, returns `Int64::min_value()` due to two's complement +/// representation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_neg" { +/// inspect!(-42L, content="-42") +/// inspect!(--42L, content="42") +/// inspect!(-9223372036854775808L, content="-9223372036854775808") // negating min value +/// } +/// ``` pub fn Int64::op_neg(self : Int64) -> Int64 = "%i64_neg" ///| +/// Adds two 64-bit integers together. Performs overflow checking and wrapping +/// according to two's complement arithmetic. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer operand. +/// * `other` : The second 64-bit integer operand to add to the first. +/// +/// Returns a new 64-bit integer representing the sum of the two operands. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_add" { +/// let a = 9223372036854775807L // Int64 maximum value +/// let b = 1L +/// inspect!(a + b, content="-9223372036854775808") // Wraps around to minimum value +/// inspect!(42L + -42L, content="0") +/// } +/// ``` pub fn Int64::op_add(self : Int64, other : Int64) -> Int64 = "%i64_add" ///| +/// Performs subtraction between two 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The minuend (the number being subtracted from). +/// * `other` : The subtrahend (the number to subtract). +/// +/// Returns the difference between `self` and `other` as a 64-bit integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_sub" { +/// let a = 9223372036854775807L // Int64 maximum value +/// let b = 1L +/// inspect!(a - b, content="9223372036854775806") +/// let c = -9223372036854775808L // Int64 minimum value +/// let d = 1L +/// inspect!(c - d, content="9223372036854775807") +/// } +/// ``` pub fn Int64::op_sub(self : Int64, other : Int64) -> Int64 = "%i64_sub" ///| +/// Multiplies two 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer operand. +/// * `other` : The second 64-bit integer operand. +/// +/// Returns the product of the two 64-bit integers. If the result overflows the +/// range of `Int64`, it will be truncated according to two's complement +/// arithmetic. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_mul" { +/// let a = 42L +/// let b = 100L +/// inspect!(a * b, content="4200") +/// let c = -42L +/// inspect!(c * b, content="-4200") +/// } +/// ``` pub fn Int64::op_mul(self : Int64, other : Int64) -> Int64 = "%i64_mul" ///| +/// Performs integer division between two 64-bit integers. Truncates the result +/// towards zero. +/// +/// Parameters: +/// +/// * `self` : The dividend (the number to be divided). +/// * `other` : The divisor (the number to divide by). +/// +/// Returns the quotient of the division. +/// +/// Throws a panic if `other` is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_div" { +/// let a = 42L +/// let b = 5L +/// inspect!(a / b, content="8") +/// let c = -42L +/// let d = 5L +/// inspect!(c / d, content="-8") +/// } +/// +/// test "panic Int64::op_div/division_by_zero" { +/// let a = 42L +/// ignore(a / 0L) // Division by zero +/// } +/// ``` pub fn Int64::op_div(self : Int64, other : Int64) -> Int64 = "%i64_div" ///| +/// Calculates the remainder of the division between two 64-bit integers. The +/// result follows the formula `self - (self / other) * other`, maintaining the +/// same sign as the dividend. +/// +/// Parameters: +/// +/// * `self` : The dividend 64-bit integer. +/// * `other` : The divisor 64-bit integer. +/// +/// Returns the remainder of the division. +/// +/// Throws a panic if `other` is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_mod" { +/// inspect!(7L % 3L, content="1") +/// inspect!(-7L % 3L, content="-1") +/// inspect!(7L % -3L, content="1") +/// } +/// +/// test "panic Int64::op_mod/division_by_zero" { +/// ignore(7L % 0L) // Panics with division by zero +/// } +/// ``` pub fn Int64::op_mod(self : Int64, other : Int64) -> Int64 = "%i64_mod" ///| +/// Performs a bitwise NOT operation on a 64-bit integer. Each bit in the input +/// value is flipped (0 becomes 1 and 1 becomes 0). +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer on which to perform the bitwise NOT operation. +/// +/// Returns a new 64-bit integer where each bit is the inverse of the +/// corresponding bit in the input value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::lnot" { +/// let a = -1L // All bits are 1 +/// let b = 0L // All bits are 0 +/// inspect!(a.lnot(), content="0") +/// inspect!(b.lnot(), content="-1") +/// } +/// ``` pub fn Int64::lnot(self : Int64) -> Int64 = "%i64_lnot" ///| +/// Performs a bitwise AND operation between two 64-bit signed integers. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer operand. +/// * `other` : The second 64-bit integer operand. +/// +/// Returns a 64-bit integer where each bit is set to 1 if and only if the +/// corresponding bits in both operands are 1. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::land" { +/// let a = 0xFF00FF00L +/// let b = 0x0F0F0F0FL +/// inspect!(a & b, content="251662080") // 0x0F000F00 +/// } +/// ``` pub fn Int64::land(self : Int64, other : Int64) -> Int64 = "%i64_land" ///| +/// Performs a bitwise OR operation between two 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer operand. +/// * `other` : The second 64-bit integer operand. +/// +/// Returns a new 64-bit integer where each bit is set to 1 if at least one of +/// the corresponding bits in either operand is 1. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::lor" { +/// let a = 0xFF00L // 1111_1111_0000_0000 +/// let b = 0x0FF0L // 0000_1111_1111_0000 +/// inspect!(a | b, content="65520") // 1111_1111_1111_0000 = 65520 +/// } +/// ``` pub fn Int64::lor(self : Int64, other : Int64) -> Int64 = "%i64_lor" ///| +/// Performs a bitwise XOR operation between two 64-bit integers. Each bit of the +/// result is set to 1 if the corresponding bits of the operands are different, +/// and 0 if they are the same. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer operand. +/// * `other` : The second 64-bit integer operand. +/// +/// Returns a new 64-bit integer containing the result of the bitwise XOR +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::lxor" { +/// let a = 0xF0F0F0F0F0F0F0F0L +/// let b = 0x0F0F0F0F0F0F0F0FL +/// inspect!(a ^ b, content="-1") // All bits set to 1 +/// inspect!(a ^ a, content="0") // XOR with self gives 0 +/// } +/// ``` pub fn Int64::lxor(self : Int64, other : Int64) -> Int64 = "%i64_lxor" ///| +/// Performs a left shift operation on a 64-bit signed integer. Shifts each bit +/// in the integer to the left by the specified number of positions, filling the +/// vacated bit positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The 64-bit signed integer to be shifted. +/// * `shift` : The number of positions to shift. Must be non-negative and less +/// than 64. +/// +/// Returns a new 64-bit integer with bits shifted left by the specified number +/// of positions. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::lsl" { +/// let x = 1L +/// inspect!(x << 2, content="4") // Binary: 1 -> 100 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn Int64::lsl(self : Int64, other : Int) -> Int64 = "%i64_shl" ///| +/// Performs a left shift operation on a 64-bit integer value. Shifts the bits of +/// the integer to the left by a specified number of positions, filling the +/// rightmost positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer value to be shifted. +/// * `shift` : The number of positions to shift the bits to the left. +/// +/// Returns a new 64-bit integer value after performing the left shift operation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::shl" { +/// let x = 1L +/// inspect!(x << 3, content="8") // Equivalent to x << 3 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn Int64::shl(self : Int64, other : Int) -> Int64 = "%i64_shl" ///| +/// **DEPRECATED:** Use `UInt64` type and infix operator `>>` instead. +/// +/// Performs a logical right shift on a 64-bit integer value. In a logical right +/// shift, zeros are shifted in from the left, regardless of the sign bit. +/// +/// Parameters: +/// +/// * `value` : The 64-bit integer value to be shifted. +/// * `shift` : The number of positions to shift right. Must be non-negative. +/// +/// Returns a new 64-bit integer value that is the result of shifting the bits of +/// `value` right by `shift` positions. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::lsr" { +/// let x = (-4L).reinterpret_as_uint64() // Convert to UInt64 first +/// inspect!(x >> 1, content="9223372036854775806") // Using the recommended operator +/// } +/// ``` +/// /// @alert deprecated "Use UInt64 type and infix operator `>>` instead" /// @coverage.skip pub fn Int64::lsr(self : Int64, other : Int) -> Int64 = "%u64.shr" ///| +/// DEPRECATED: Use the infix operator `>>` instead. +/// +/// Performs an arithmetic right shift operation on a 64-bit integer. In an +/// arithmetic right shift, the leftmost bit (sign bit) is copied to fill in from +/// the left. This preserves the sign of the number. +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer to be shifted. +/// * `positions` : The number of positions to shift right. Must be non-negative. +/// +/// Returns a new 64-bit integer that is the result of shifting `self` right by +/// `positions` bits, with sign extension. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::asr" { +/// let x = -240L // 0b1111_1111_0001_0000 in two's complement +/// inspect!(x >> 4, content="-15") // 0b1111_1111_1111_0001, using recommended syntax +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip pub fn Int64::asr(self : Int64, other : Int) -> Int64 = "%i64_shr" ///| +/// Performs an arithmetic right shift operation on a 64-bit integer value, +/// shifting the bits to the right by the specified number of positions. The sign +/// bit is copied to fill the leftmost positions. +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer value to be shifted. +/// * `shift` : The number of bit positions to shift right. Must be non-negative. +/// +/// Returns a new `Int64` value representing the result of the arithmetic right +/// shift operation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::shr" { +/// let n = -1024L +/// inspect!(n >> 3, content="-128") // Preserves sign bit +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip pub fn Int64::shr(self : Int64, other : Int) -> Int64 = "%i64_shr" ///| +/// Performs a left shift operation on a 64-bit integer value. Shifts the bits of +/// the first operand to the left by the number of positions specified by the +/// second operand. The rightmost positions are filled with zeros. +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer value to be shifted. +/// * `shift` : The number of positions to shift the bits to the left. Must be +/// non-negative and less than 64. +/// +/// Returns a new `Int64` value representing the result of the left shift +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_shl" { +/// let n = 1L +/// inspect!(n << 3, content="8") // 1 shifted left by 3 positions becomes 8 +/// let m = -4L +/// inspect!(m << 2, content="-16") // -4 shifted left by 2 positions becomes -16 +/// } +/// ``` pub fn Int64::op_shl(self : Int64, other : Int) -> Int64 = "%i64_shl" ///| +/// Performs arithmetic right shift operation on a 64-bit integer value by a +/// specified number of bits. Preserves the sign bit of the original number while +/// shifting its bits right, filling the leftmost positions with copies of the +/// sign bit. +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer value to be shifted. +/// * `shift_count` : The number of positions to shift right. Must be +/// non-negative and less than 64. +/// +/// Returns a new `Int64` value that represents the result of shifting `self` +/// right by `shift_count` bits. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_shr" { +/// let n = -1024L +/// inspect!(n >> 3, content="-128") // Preserves sign bit +/// let p = 1024L +/// inspect!(p >> 3, content="128") // Regular right shift for positive numbers +/// } +/// ``` pub fn Int64::op_shr(self : Int64, other : Int) -> Int64 = "%i64_shr" ///| +/// Returns the number of trailing zero bits in a 64-bit integer. For zero input, +/// returns 64. +/// +/// Parameters: +/// +/// * `value` : The 64-bit integer to count trailing zeros in. +/// +/// Returns the number of trailing zero bits (0 to 64). +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::ctz" { +/// inspect!(0x8000000000000000L.ctz(), content="63") // Binary: 1000...0000 +/// inspect!(0x0000000000000001L.ctz(), content="0") // Binary: ...0001 +/// inspect!(0L.ctz(), content="64") // All zeros +/// } +/// ``` pub fn Int64::ctz(self : Int64) -> Int = "%i64_ctz" ///| +/// Counts the number of leading zero bits in a 64-bit signed integer, starting +/// from the most significant bit. +/// +/// Parameters: +/// +/// * `number` : The 64-bit signed integer whose leading zeros are to be counted. +/// +/// Returns the number of leading zero bits (0 to 64). +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::clz" { +/// let a = 0x0000_0001_0000_0000L +/// inspect!(a.clz(), content="31") // 31 leading zeros before the first 1 bit +/// let b = 0L +/// inspect!(b.clz(), content="64") // All bits are zero +/// } +/// ``` pub fn Int64::clz(self : Int64) -> Int = "%i64_clz" ///| +/// Returns the number of 1 bits ('population count') in the 64-bit integer's +/// binary representation. +/// +/// Parameters: +/// +/// * `value` : The 64-bit integer whose bits are to be counted. +/// +/// Returns an integer representing the number of set bits (1s) in the binary +/// representation of the input. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::popcnt" { +/// let x = 0x7000_0001_1F00_100FL // 0111000000000000000000000001000111110000000100001111 +/// inspect!(x.popcnt(), content="14") +/// } +/// ``` +/// +/// ```moonbit +/// test "Int64::popcnt/edge_cases" { +/// inspect!((-1L).popcnt(), content="64") // All bits set +/// inspect!(0L.popcnt(), content="0") // No bits set +/// } +/// ``` pub fn Int64::popcnt(self : Int64) -> Int = "%i64_popcnt" ///| +/// Tests if two 64-bit integers are equal. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer to compare. +/// * `other` : The second 64-bit integer to compare. +/// +/// Returns `true` if both integers are equal, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::op_equal" { +/// let a = 42L +/// let b = 42L +/// let c = -42L +/// inspect!(a == b, content="true") +/// inspect!(a == c, content="false") +/// } +/// ``` pub fn Int64::op_equal(self : Int64, other : Int64) -> Bool = "%i64_eq" ///| +/// Compares two 64-bit integers and returns their relative order. +/// +/// Parameters: +/// +/// * `self` : The first 64-bit integer to compare. +/// * `other` : The second 64-bit integer to compare against. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::compare" { +/// let a = 42L +/// let b = 24L +/// let c = -42L +/// inspect!(a.compare(b), content="1") // 42 > 24 +/// inspect!(b.compare(a), content="-1") // 24 < 42 +/// inspect!(c.compare(a), content="-1") // -42 < 42 +/// inspect!(a.compare(a), content="0") // 42 = 42 +/// } +/// ``` pub fn Int64::compare(self : Int64, other : Int64) -> Int = "%i64_compare" ///| +/// Returns the default value for `Int64` type, which is zero (0L). +/// +/// Returns a 64-bit signed integer with value 0. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::default" { +/// inspect!(Int64::default(), content="0") +/// } +/// ``` pub fn Int64::default() -> Int64 = "%i64_default" ///| +/// Converts a 64-bit signed integer to a 32-bit signed integer by truncating +/// higher bits. +/// +/// Parameters: +/// +/// * `value` : The 64-bit signed integer (`Int64`) to be converted. +/// +/// Returns a 32-bit signed integer (`Int`). Note that values outside the range +/// of 32-bit integers will be truncated, potentially leading to loss of +/// information. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_int" { +/// let small = 42L +/// let big = 2147483648L // 2^31 +/// inspect!(small.to_int(), content="42") +/// inspect!(big.to_int(), content="-2147483648") // Truncated to Int.min_value +/// } +/// ``` pub fn Int64::to_int(self : Int64) -> Int = "%i64_to_i32" ///| +/// Converts a 64-bit signed integer to a double-precision floating-point number. +/// +/// Parameters: +/// +/// * `self` : The 64-bit signed integer to be converted. +/// +/// Returns a double-precision floating-point number that represents the same +/// value as the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_double" { +/// let big = 9223372036854775807L // max value of Int64 +/// inspect!(big.to_double(), content="9223372036854776000") +/// let neg = -42L +/// inspect!(neg.to_double(), content="-42") +/// } +/// ``` pub fn Int64::to_double(self : Int64) -> Double = "%i64_to_f64" ///| +/// Reinterprets the bits of a 64-bit signed integer as a double-precision +/// floating-point number (IEEE 754). The bit pattern is preserved exactly, only +/// the type interpretation changes. +/// +/// Parameters: +/// +/// * `value` : The 64-bit signed integer whose bits are to be reinterpreted as a +/// double-precision floating-point number. +/// +/// Returns a double-precision floating-point number whose bit pattern is +/// identical to the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::reinterpret_as_double" { +/// let n = 4607182418800017408L // Bit pattern for 1.0 +/// inspect!(n.reinterpret_as_double(), content="1") +/// } +/// ``` pub fn Int64::reinterpret_as_double(self : Int64) -> Double = "%i64_to_f64_reinterpret" ///| +/// Reinterprets the bits of an unsigned 64-bit integer as a double-precision +/// floating-point number according to IEEE 754 standard. The bit pattern of the +/// input is preserved, only the type interpretation changes. +/// +/// Parameters: +/// +/// * `value` : The unsigned 64-bit integer whose bits are to be reinterpreted as +/// a double-precision floating-point number. +/// +/// Returns a double-precision floating-point number that has the same bit +/// pattern as the input unsigned 64-bit integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::reinterpret_as_double" { +/// // 0x4045000000000000 represents 42.0 in IEEE 754 double format +/// let n = 4636737291354636288UL +/// inspect!(n.reinterpret_as_double(), content="100") +/// } +/// ``` pub fn UInt64::reinterpret_as_double(self : UInt64) -> Double = "%i64_to_f64_reinterpret" ///| +/// Converts a 64-bit signed integer to a byte by taking its least significant 8 +/// bits. Any bits beyond the first 8 bits are truncated. +/// +/// Parameters: +/// +/// * `self` : The 64-bit signed integer to be converted. Only the least +/// significant 8 bits will be used. +/// +/// Returns a byte containing the least significant 8 bits of the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_byte" { +/// let n = 258L // In binary: 100000010 +/// inspect!(n.to_byte(), content="b'\\x02'") // Only keeps 00000010 +/// let neg = -1L // In binary: all 1's +/// inspect!(neg.to_byte(), content="b'\\xFF'") // Only keeps 11111111 +/// } +/// ``` pub fn Int64::to_byte(self : Int64) -> Byte = "%i64_to_byte" ///| +/// Converts a 64-bit signed integer to a 16-bit signed integer by truncating the +/// value to fit within the 16-bit range (-32768 to 32767). +/// +/// Parameters: +/// +/// * `value` : The 64-bit signed integer to be converted. +/// +/// Returns a 16-bit signed integer representing the lower 16 bits of the input +/// value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_int16" { +/// let big = 100000L +/// inspect!(big.to_int16(), content="-31072") // 100000 doesn't fit in Int16, gets truncated +/// let small = 42L +/// inspect!(small.to_int16(), content="42") // 42 fits in Int16, remains unchanged +/// } +/// ``` pub fn Int64::to_int16(self : Int64) -> Int16 = "%i64_to_i16" ///| +/// Converts a 64-bit signed integer to a 16-bit unsigned integer by truncating +/// the value to fit within the range of UInt16 (0 to 65535). +/// +/// Parameters: +/// +/// * `value` : The 64-bit signed integer to be converted to UInt16. +/// +/// Returns a 16-bit unsigned integer representing the lower 16 bits of the input +/// value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_uint16" { +/// inspect!(42L.to_uint16(), content="42") +/// inspect!((-1L).to_uint16(), content="65535") // Wraps around to maximum UInt16 value +/// inspect!(70000L.to_uint16(), content="4464") // Value is truncated +/// } +/// ``` pub fn Int64::to_uint16(self : Int64) -> UInt16 = "%i64_to_u16" ///| +/// Converts a double-precision floating-point number to an unsigned 64-bit +/// integer by truncating its decimal part. This is a raw conversion function +/// that does not handle special cases like NaN or infinity. +/// +/// Parameters: +/// +/// * `value` : The double-precision floating-point number to be truncated and +/// converted. +/// +/// Returns an unsigned 64-bit integer. The decimal part of the input is +/// discarded (truncated towards zero). +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::trunc_double" { +/// inspect!(UInt64::trunc_double(42.75), content="42") +/// } +/// ``` pub fn UInt64::trunc_double(val : Double) -> UInt64 = "%f64.to_u64" ///| +/// Converts a 64-bit integer to a 32-bit floating-point number. The conversion +/// may result in loss of precision due to the limited precision of the 32-bit +/// floating-point format. +/// +/// Parameters: +/// +/// * `self` : The 64-bit integer value to be converted. +/// +/// Returns a 32-bit floating-point number that represents the input integer +/// value. Note that for values outside the range of representable 32-bit +/// floating-point numbers, the result will be rounded to the nearest +/// representable value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_float" { +/// let n = 42L +/// let f = n.to_float() +/// // Convert to double for comparison since Float doesn't implement Show +/// inspect!(f.to_double(), content="42") +/// } +/// ``` pub fn Int64::to_float(self : Int64) -> Float = "%i64.to_f32" ///| +/// Converts an unsigned 32-bit integer to an unsigned 64-bit integer by +/// zero-extending it. The resulting value preserves the original number's +/// magnitude while using 64 bits to represent it. +/// +/// Parameters: +/// +/// * `value` : The unsigned 32-bit integer (`UInt`) to be converted. +/// +/// Returns an unsigned 64-bit integer (`UInt64`) representing the same numerical +/// value as the input. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::extend_uint" { +/// let n = 42U +/// inspect!(UInt64::extend_uint(n), content="42") +/// let max = 4294967295U // Maximum value of UInt +/// inspect!(UInt64::extend_uint(max), content="4294967295") +/// } +/// ``` pub fn UInt64::extend_uint(val : UInt) -> UInt64 = "%u32.to_u64" ///| +/// Converts a 32-bit signed integer to a 64-bit signed integer. All 32-bit +/// integers can be represented exactly in 64-bit integer format, so the +/// conversion is lossless. +/// +/// Parameters: +/// +/// * `self` : The 32-bit signed integer to be converted. +/// +/// Returns a 64-bit signed integer that represents the same numerical value as +/// the input. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_int64" { +/// let n = 42 +/// inspect!(n.to_int64(), content="42") +/// let neg = -42 +/// inspect!(neg.to_int64(), content="-42") +/// } +/// ``` pub fn Int::to_int64(self : Int) -> Int64 = "%i32_to_i64" ///| pub fn Int16::to_int64(self : Int16) -> Int64 = "%i16_to_i64" ///| +/// Converts an unsigned 16-bit integer to a signed 64-bit integer. The resulting +/// value will always be non-negative since the input is unsigned. +/// +/// Parameters: +/// +/// * `value` : The unsigned 16-bit integer to be converted. +/// +/// Returns a 64-bit signed integer representing the same numerical value as the +/// input. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt16::to_int64" { +/// let x = Int::to_uint16(42) +/// inspect!(x.to_int64(), content="42") +/// let max = Int::to_uint16(65535) // maximum value of UInt16 +/// inspect!(max.to_int64(), content="65535") +/// } +/// ``` pub fn UInt16::to_int64(self : UInt16) -> Int64 = "%u16_to_i64" ///| +/// Reinterprets the bits of a double-precision floating-point number as a 64-bit +/// signed integer without any conversion. This is a low-level operation that +/// simply reinterprets the bit pattern of the input value. +/// +/// Parameters: +/// +/// * `value` : The double-precision floating-point number whose bits are to be +/// reinterpreted. +/// +/// Returns a 64-bit signed integer that has the same bit pattern as the input +/// double-precision floating-point number. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::reinterpret_as_i64" { +/// let d = 1.0 +/// // 1.0 in IEEE 754 double format has the bit pattern 0x3FF0000000000000 +/// inspect!(d.reinterpret_as_int64(), content="4607182418800017408") +/// } +/// ``` +/// /// @alert deprecated "Use `reinterpret_as_int64` instead" /// @coverage.skip pub fn Double::reinterpret_as_i64(self : Double) -> Int64 = "%f64_to_i64_reinterpret" ///| +/// Reinterprets the bits of a double-precision floating-point number as a 64-bit +/// signed integer without performing any conversion. Preserves the exact bit +/// pattern of the input value. +/// +/// Parameters: +/// +/// * `number` : The double-precision floating-point number whose bits will be +/// reinterpreted. +/// +/// Returns a 64-bit signed integer containing the same bit pattern as the input +/// floating-point number. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::reinterpret_as_int64" { +/// let d = 1.0 +/// inspect!(d.reinterpret_as_int64(), content="4607182418800017408") // IEEE 754 representation of 1.0 +/// let neg = -0.0 +/// inspect!(neg.reinterpret_as_int64(), content="-9223372036854775808") // Sign bit set +/// } +/// ``` pub fn Double::reinterpret_as_int64(self : Double) -> Int64 = "%f64_to_i64_reinterpret" ///| +/// Reinterprets the bits of a double-precision floating-point number as an +/// unsigned 64-bit integer. The bit pattern is preserved during the conversion, +/// with no mathematical conversion performed. +/// +/// Parameters: +/// +/// * `self` : The double-precision floating-point number to be reinterpreted. +/// +/// Returns an unsigned 64-bit integer containing the same bit pattern as the +/// input floating-point number. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::reinterpret_as_u64" { +/// let zero = 0.0 +/// let positive = 1.0 +/// inspect!(zero.reinterpret_as_uint64(), content="0") +/// inspect!(positive.reinterpret_as_uint64(), content="4607182418800017408") +/// } +/// ``` +/// /// @alert deprecated "Use `reinterpret_as_uint64` instead" /// @coverage.skip pub fn Double::reinterpret_as_u64(self : Double) -> UInt64 = "%f64_to_i64_reinterpret" ///| +/// Reinterprets the bits of a double-precision floating-point number as an +/// unsigned 64-bit integer, preserving the exact bit pattern without performing +/// any numerical conversion. +/// +/// Parameters: +/// +/// * `self` : The double-precision floating-point number whose bits will be +/// reinterpreted. +/// +/// Returns an unsigned 64-bit integer that has the same bit pattern as the input +/// floating-point number. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::reinterpret_as_uint64" { +/// let d = 1.0 +/// inspect!(d.reinterpret_as_uint64(), content="4607182418800017408") // Binary: 0x3FF0000000000000 +/// } +/// ``` pub fn Double::reinterpret_as_uint64(self : Double) -> UInt64 = "%f64_to_i64_reinterpret" ///| +/// Converts an unsigned 64-bit integer to a double-precision floating-point +/// number. The conversion is exact for integers up to 53 bits (the size of the +/// mantissa in a double-precision number), but may lose precision for larger +/// values. +/// +/// Parameters: +/// +/// * `value` : The unsigned 64-bit integer to be converted. +/// +/// Returns a double-precision floating-point number representing the same +/// numerical value as the input. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::convert_uint64" { +/// let n = 12345678901234567890UL +/// inspect!(Double::convert_uint64(n), content="12345678901234567000") +/// } +/// ``` pub fn Double::convert_uint64(val : UInt64) -> Double = "%u64.to_f64" ///| +/// Reinterprets a 64-bit signed integer as an unsigned 64-bit integer without +/// changing its bits. When the value is non-negative, i.e., within the range +/// \[0, 2^63-1], the value remains the same. When the value is negative, it +/// becomes a large number in the range \[2^63, 2^64-1]. +/// +/// Parameters: +/// +/// * `value` : The 64-bit signed integer (`Int64`) to be reinterpreted. +/// +/// Returns an unsigned 64-bit integer (`UInt64`) containing the same bit pattern +/// as the input. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::to_uint64" { +/// let pos = 42L +/// let neg = -1L +/// inspect!(pos.reinterpret_as_uint64(), content="42") +/// inspect!(neg.reinterpret_as_uint64(), content="18446744073709551615") // 2^64 - 1 +/// } +/// ``` +/// /// @alert deprecated "Use `reinterpret_as_uint64` instead" /// @coverage.skip pub fn Int64::to_uint64(self : Int64) -> UInt64 = "%i64.to_u64_reinterpret" ///| +/// Reinterprets a 64-bit signed integer as an unsigned 64-bit integer without +/// changing its bit pattern. The reinterpretation follows the standard two's +/// complement representation rules. +/// +/// Parameters: +/// +/// * `self` : The 64-bit signed integer to be reinterpreted. +/// +/// Returns a 64-bit unsigned integer that has the same bit pattern as the input. +/// +/// Example: +/// +/// ```moonbit +/// test "Int64::reinterpret_as_uint64" { +/// let neg = -1L +/// inspect!(neg.reinterpret_as_uint64(), content="18446744073709551615") // All bits set to 1 +/// let pos = 42L +/// inspect!(pos.reinterpret_as_uint64(), content="42") // Positive numbers remain unchanged +/// } +/// ``` pub fn Int64::reinterpret_as_uint64(self : Int64) -> UInt64 = "%i64.to_u64_reinterpret" ///| +/// Reinterprets a 64-bit unsigned integer as a 64-bit signed integer. The bits +/// of the number remain unchanged; only the interpretation of these bits +/// changes. This function is deprecated; use `reinterpret_as_int64` instead. +/// +/// Parameters: +/// +/// * `value` : The 64-bit unsigned integer to be reinterpreted. +/// +/// Returns a 64-bit signed integer representing the same bit pattern as the +/// input. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::reinterpret_as_int64" { +/// let max = 18446744073709551615UL +/// inspect!(max.reinterpret_as_int64(), content="-1") +/// } +/// ``` +/// /// @alert deprecated "Use `reinterpret_as_int64` instead" /// @coverage.skip pub fn UInt64::to_int64(self : UInt64) -> Int64 = "%u64.to_i64_reinterpret" ///| +/// Reinterprets the bits of an unsigned 64-bit integer as a signed 64-bit +/// integer. The bits remain the same, but their interpretation changes. This +/// operation is useful for low-level bit manipulation and type conversions where +/// you want to preserve the exact bit pattern. +/// +/// Parameters: +/// +/// * `value` : The unsigned 64-bit integer (`UInt64`) to be reinterpreted. +/// +/// Returns a signed 64-bit integer (`Int64`) that has the same bit pattern as +/// the input value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::reinterpret_as_int64" { +/// let max = 18446744073709551615UL // Maximum value of UInt64 +/// inspect!(max.reinterpret_as_int64(), content="-1") // All bits set to 1 represents -1 in two's complement +/// } +/// ``` pub fn UInt64::reinterpret_as_int64(self : UInt64) -> Int64 = "%u64.to_i64_reinterpret" ///| +/// Converts a 64-bit unsigned integer to a 32-bit unsigned integer by truncating +/// the higher 32 bits. +/// +/// Parameters: +/// +/// * `self` : The 64-bit unsigned integer to be converted. +/// +/// Returns a 32-bit unsigned integer containing the lower 32 bits of the input +/// value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::to_uint" { +/// let big = 0xFFFFFFFFFFFFFFFFUL // max value of UInt64 +/// inspect!(big.to_uint(), content="4294967295") // 0xFFFFFFFF, max value of UInt +/// let small = 42UL +/// inspect!(small.to_uint(), content="42") +/// } +/// ``` pub fn UInt64::to_uint(self : UInt64) -> UInt = "%u64.to_u32" ///| +/// Converts an unsigned 64-bit integer to a 32-bit signed integer. The +/// conversion truncates the value to fit within the 32-bit range, possibly +/// losing information if the input value is too large. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer to be converted. +/// +/// Returns a 32-bit signed integer representing the lower 32 bits of the input +/// value. If the input value is larger than the maximum value of a 32-bit signed +/// integer (2147483647), the result will be the truncated value interpreted as a +/// signed integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::to_int" { +/// let a = 42UL +/// inspect!(a.to_int(), content="42") +/// let b = 18446744073709551615UL // max value of UInt64 +/// inspect!(b.to_int(), content="-1") // truncated to 32 bits +/// } +/// ``` pub fn UInt64::to_int(self : UInt64) -> Int = "%u64.to_i32" ///| +/// Converts an unsigned 64-bit integer to a double-precision floating-point +/// number. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer (`UInt64`) to be converted. +/// +/// Returns a double-precision floating-point number (`Double`) that represents +/// the same numerical value as the input. Note that due to the limited precision +/// of double-precision floating-point numbers, values larger than 2^53 may lose +/// precision during the conversion. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::to_double" { +/// let n = 12345678901234567890UL +/// inspect!(n.to_double(), content="12345678901234567000") // Note the slight precision loss +/// let small = 42UL +/// inspect!(small.to_double(), content="42") +/// } +/// ``` pub fn UInt64::to_double(self : UInt64) -> Double = "%u64.to_f64" ///| +/// Adds two 64-bit unsigned integers. This is the implementation of the `+` +/// operator for `UInt64`. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer operand. +/// * `other` : The second unsigned 64-bit integer operand. +/// +/// Returns the sum of the two unsigned 64-bit integers. If the result overflows, +/// it wraps around modulo 2^64. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_add" { +/// let a = 42UL +/// let b = 100UL +/// inspect!(a + b, content="142") +/// +/// // Demonstrate overflow behavior +/// let max = 18446744073709551615UL +/// inspect!(max + 1UL, content="0") +/// } +/// ``` pub fn UInt64::op_add(self : UInt64, other : UInt64) -> UInt64 = "%u64.add" ///| +/// Performs subtraction between two unsigned 64-bit integers. When the result +/// would be negative, the function wraps around using modular arithmetic (2^64). +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer (minuend). +/// * `other` : The second unsigned 64-bit integer to subtract from the first +/// (subtrahend). +/// +/// Returns the difference between the two numbers, wrapped around if necessary. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_sub" { +/// let a = 5UL +/// let b = 3UL +/// inspect!(a - b, content="2") +/// let c = 3UL +/// let d = 5UL +/// inspect!(c - d, content="18446744073709551614") // wraps around to 2^64 - 2 +/// } +/// ``` pub fn UInt64::op_sub(self : UInt64, other : UInt64) -> UInt64 = "%u64.sub" ///| +/// Performs multiplication between two unsigned 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer operand. +/// * `other` : The second unsigned 64-bit integer operand. +/// +/// Returns the product of the two unsigned 64-bit integers. The result wraps +/// around if it exceeds the maximum value of `UInt64`. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_mul" { +/// let a = 2UL +/// let b = 3UL +/// inspect!(a * b, content="6") +/// +/// // Demonstrate wrapping behavior +/// let max = 18446744073709551615UL +/// inspect!(max * 2UL, content="18446744073709551614") // Wraps around to max - 1 +/// } +/// ``` pub fn UInt64::op_mul(self : UInt64, other : UInt64) -> UInt64 = "%u64.mul" ///| +/// Performs division operation between two unsigned 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The dividend unsigned 64-bit integer. +/// * `other` : The divisor unsigned 64-bit integer. +/// +/// Returns the quotient of dividing the dividend by the divisor. +/// +/// Throws a runtime error if `other` is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_div" { +/// let a = 100UL +/// let b = 20UL +/// inspect!(a / b, content="5") // Using infix operator +/// } +/// +/// test "panic UInt64::op_div/division_by_zero" { +/// let a = 42UL +/// ignore(a / 0UL) // Throws runtime error: division by zero +/// } +/// ``` pub fn UInt64::op_div(self : UInt64, other : UInt64) -> UInt64 = "%u64.div" ///| +/// Calculates the remainder of dividing one unsigned 64-bit integer by another. +/// +/// Parameters: +/// +/// * `self` : The dividend unsigned 64-bit integer. +/// * `other` : The divisor unsigned 64-bit integer. +/// +/// Returns the remainder of the division operation. +/// +/// Throws a panic if the divisor is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_mod" { +/// let a = 17UL +/// let b = 5UL +/// inspect!(a % b, content="2") // 17 divided by 5 gives quotient 3 and remainder 2 +/// inspect!(7UL % 4UL, content="3") +/// } +/// +/// test "panic UInt64::op_mod/division_by_zero" { +/// let a = 42UL +/// ignore(a % 0UL) // Panics: division by zero +/// } +/// ``` pub fn UInt64::op_mod(self : UInt64, other : UInt64) -> UInt64 = "%u64.mod" ///| +/// Compares two unsigned 64-bit integers and determines their relative order. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer to compare. +/// * `other` : The second unsigned 64-bit integer to compare. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::compare" { +/// let a = 42UL +/// let b = 24UL +/// inspect!(a.compare(b), content="1") // 42 > 24 +/// inspect!(b.compare(a), content="-1") // 24 < 42 +/// inspect!(a.compare(a), content="0") // 42 = 42 +/// } +/// ``` pub fn UInt64::compare(self : UInt64, other : UInt64) -> Int = "%u64.compare" ///| +/// Compares two unsigned 64-bit integers for equality. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer to compare. +/// * `other` : The second unsigned 64-bit integer to compare. +/// +/// Returns `true` if both integers have the same value, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_equal" { +/// let a = 42UL +/// let b = 42UL +/// let c = 24UL +/// inspect!(a == b, content="true") +/// inspect!(a == c, content="false") +/// } +/// ``` pub fn UInt64::op_equal(self : UInt64, other : UInt64) -> Bool = "%u64.eq" ///| +/// Performs a bitwise AND operation between two unsigned 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer operand. +/// * `other` : The second unsigned 64-bit integer operand. +/// +/// Returns the result of performing a bitwise AND operation on the two operands. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::land" { +/// let a = 0xF0F0F0F0F0F0F0F0UL +/// let b = 0xFF00FF00FF00FF00UL +/// inspect!(a & b, content="17294086455919964160") // 0xF000F000F000F000 +/// } +/// ``` pub fn UInt64::land(self : UInt64, other : UInt64) -> UInt64 = "%u64.bitand" ///| +/// Performs a bitwise OR operation between two unsigned 64-bit integers. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer operand. +/// * `other` : The second unsigned 64-bit integer operand. +/// +/// Returns a new `UInt64` value with bits set to 1 where either or both operands +/// have bits set to 1, and 0 where both operands have bits set to 0. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::lor" { +/// let a = 0xF0F0F0F0UL +/// let b = 0x0F0F0F0FUL +/// inspect!(a | b, content="4294967295") // All bits set to 1 +/// } +/// ``` pub fn UInt64::lor(self : UInt64, other : UInt64) -> UInt64 = "%u64.bitor" ///| +/// Performs a bitwise XOR operation between two unsigned 64-bit integers. For +/// each bit position, the result is 1 if the bits at that position in the two +/// operands are different, and 0 if they are the same. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 64-bit integer operand. +/// * `other` : The second unsigned 64-bit integer operand. +/// +/// Returns a new `UInt64` value representing the bitwise XOR of the two +/// operands. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::lxor" { +/// let a = 0xF0F0F0F0UL +/// let b = 0x0F0F0F0FUL +/// inspect!(a ^ b, content="4294967295") // 0xFFFFFFFF +/// } +/// ``` pub fn UInt64::lxor(self : UInt64, other : UInt64) -> UInt64 = "%u64.bitxor" ///| +/// Performs a bitwise NOT operation on a 64-bit unsigned integer. Flips all bits +/// in the number, changing each 0 to 1 and each 1 to 0. +/// +/// Parameters: +/// +/// * `self` : The 64-bit unsigned integer value on which to perform the bitwise +/// NOT operation. +/// +/// Returns a new `UInt64` value with all bits flipped from the input value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::lnot" { +/// let x = 0xFFFF_FFFF_0000_0000UL +/// inspect!(x.lnot(), content="4294967295") // 0x0000_0000_FFFF_FFFF +/// } +/// ``` pub fn UInt64::lnot(self : UInt64) -> UInt64 = "%u64.bitnot" ///| +/// Performs a left shift operation on a 64-bit unsigned integer by a specified +/// number of bits. +/// +/// Parameters: +/// +/// * `value` : The 64-bit unsigned integer to be shifted. +/// * `shift` : The number of positions to shift left. Only the lowest 6 bits are +/// used, effectively making the shift value wrap around at 64. +/// +/// Returns a new `UInt64` value representing the result of shifting the bits +/// left by the specified number of positions. Bits shifted beyond the 64-bit +/// boundary are discarded, and zeros are shifted in from the right. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::lsl" { +/// let x = 1UL +/// inspect!(x << 4, content="16") // 1 << 4 = 16 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn UInt64::lsl(self : UInt64, shift : Int) -> UInt64 = "%u64.shl" ///| +/// Performs a left shift operation on an unsigned 64-bit integer value, shifting +/// bits to the left by the specified number of positions. +/// +/// Parameters: +/// +/// * `number` : The unsigned 64-bit integer to be shifted. +/// * `shift` : The number of positions to shift the bits left. Must be +/// non-negative. +/// +/// Returns an unsigned 64-bit integer representing the result of the left shift +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::shl" { +/// let x = 1UL +/// inspect!(x << 2, content="4") // 1 << 2 = 4 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn UInt64::shl(self : UInt64, shift : Int) -> UInt64 = "%u64.shl" ///| +/// Performs a logical right shift on an unsigned 64-bit integer by a specified +/// number of bit positions. All bits shifted in from the left are zeros. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer to be shifted. +/// * `shift` : The number of positions to shift right. +/// +/// Returns the result of shifting the bits in `self` right by `shift` positions. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::shr" { +/// let x = 0xFF00000000000000UL +/// inspect!(x >> 8, content="71776119061217280") +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip pub fn UInt64::shr(self : UInt64, shift : Int) -> UInt64 = "%u64.shr" ///| +/// Performs a logical right shift operation on a 64-bit unsigned integer. Moves +/// all bits to the right by a specified number of positions, filling the +/// leftmost bits with zeros. +/// +/// Parameters: +/// +/// * `self` : The 64-bit unsigned integer to be shifted. +/// * `shift` : The number of positions to shift right. If this value is negative +/// or greater than 63, the behavior is undefined. +/// +/// Returns a new `UInt64` value containing the result of the right shift +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::lsr" { +/// let x = 0xF000000000000000UL +/// inspect!(x >> 4, content="1080863910568919040") // 0x0F00000000000000 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip pub fn UInt64::lsr(self : UInt64, shift : Int) -> UInt64 = "%u64.shr" ///| +/// Performs a bitwise left shift operation on an unsigned 64-bit integer. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer to be shifted. +/// * `shift` : The number of positions to shift the bits to the left. Must be +/// between 0 and 63 inclusive, values outside this range will be masked with `& +/// 63`. +/// +/// Returns the result of shifting `self` left by `shift` positions. For each +/// position shifted, the rightmost bit is filled with 0, and the leftmost bit is +/// discarded. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_shl" { +/// let x = 1UL +/// inspect!(x << 3, content="8") // 1 shifted left by 3 positions becomes 8 +/// inspect!(x << 63, content="9223372036854775808") // 1 shifted left by 63 positions +/// } +/// ``` pub fn UInt64::op_shl(self : UInt64, shift : Int) -> UInt64 = "%u64.shl" ///| +/// Performs a logical right shift operation on a 64-bit unsigned integer by a +/// specified number of bits. All bits shifted beyond the least significant bit +/// are discarded, and zeros are shifted in from the most significant bit. +/// +/// Parameters: +/// +/// * `self` : The 64-bit unsigned integer to be shifted. +/// * `shift` : The number of positions to shift right. Only the least +/// significant 6 bits of this value are used, effectively making the shift count +/// always between 0 and 63. +/// +/// Returns a new `UInt64` value representing the result of the right shift +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::op_shr" { +/// let x = 0xFF00FF00FF00FF00UL +/// inspect!(x >> 8, content="71777214294589695") // Shifted right by 8 bits +/// inspect!(x >> 64, content="18374966859414961920") // Equivalent to x >> 0 due to masking +/// } +/// ``` pub fn UInt64::op_shr(self : UInt64, shift : Int) -> UInt64 = "%u64.shr" ///| +/// Counts the number of leading zero bits in a 64-bit unsigned integer, starting +/// from the most significant bit. +/// +/// Parameters: +/// +/// * `value` : The 64-bit unsigned integer to count leading zeros in. +/// +/// Returns the number of consecutive zeros starting from the most significant +/// bit. For a zero value, returns 64. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::clz" { +/// inspect!(0UL.clz(), content="64") +/// inspect!(1UL.clz(), content="63") +/// inspect!(0x8000_0000_0000_0000UL.clz(), content="0") +/// } +/// ``` pub fn UInt64::clz(self : UInt64) -> Int = "%u64.clz" ///| +/// Counts the number of trailing zero bits in a 64-bit unsigned integer. The +/// trailing zeros are the contiguous zeros at the least significant end of the +/// binary representation. +/// +/// Parameters: +/// +/// * `value` : The 64-bit unsigned integer to count trailing zeros in. +/// +/// Returns the number of trailing zero bits in the input value. If the input is +/// 0, returns 64. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::ctz" { +/// let x = 0x8000000000000000UL // Binary: 1000...0000 (63 trailing zeros) +/// inspect!(x.ctz(), content="63") +/// let y = 0UL +/// inspect!(y.ctz(), content="64") +/// } +/// ``` pub fn UInt64::ctz(self : UInt64) -> Int = "%u64.ctz" ///| +/// Counts the number of bits set to 1 in the binary representation of an +/// unsigned 64-bit integer. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer whose bits are to be counted. +/// +/// Returns an integer representing the number of 1 bits (population count) in +/// the binary representation of the input. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::popcnt" { +/// let n = 0x7000_0001_1F00_100FUL // Binary: 0111 0000 ... 0001 1111 0000 0000 0001 0000 0000 1111 +/// inspect!(n.popcnt(), content="14") // Has 14 bits set to 1 +/// } +/// ``` pub fn UInt64::popcnt(self : UInt64) -> Int = "%u64.popcnt" ///| +/// Converts an unsigned 64-bit integer to a 32-bit floating-point number. Due to +/// floating-point precision limitations, the conversion may lose precision if +/// the integer value is too large to be represented exactly as a float. +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer to be converted. +/// +/// Returns a 32-bit floating-point number that represents the input value. If +/// the input value is too large to be represented exactly, the result will be +/// rounded to the nearest representable float value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::to_float" { +/// let n = 42UL +/// inspect!(n.to_float().to_double(), content="42") +/// let big = 18446744073709551615UL // UInt64::max_value +/// inspect!(big.to_float().to_double(), content="18446744073709552000") +/// } +/// ``` pub fn UInt64::to_float(self : UInt64) -> Float = "%u64.to_f32" diff --git a/builtin/intrinsics.mbt b/builtin/intrinsics.mbt index 255953e69..d2470877b 100644 --- a/builtin/intrinsics.mbt +++ b/builtin/intrinsics.mbt @@ -13,12 +13,75 @@ // limitations under the License. ///| +/// Evaluates an expression and discards its result. This is useful when you want +/// to execute an expression for its side effects but don't care about its return +/// value, or when you want to explicitly indicate that a value is intentionally +/// unused. +/// +/// Parameters: +/// +/// * `value` : The value to be ignored. Can be of any type. +/// +/// Example: +/// +/// ```moonbit +/// test "ignore" { +/// let x = 42 +/// ignore(x) // Explicitly ignore the value +/// let mut sum = 0 +/// ignore([1, 2, 3].iter().each(fn(x) { sum = sum + x })) // Ignore the Unit return value of each() +/// } +/// ``` + pub fn ignore[T](t : T) -> Unit = "%ignore" ///| +/// Tests if two values are physically equal (i.e., point to the same memory +/// location). Unlike structural equality testing (`==`), this function checks if +/// two references point to exactly the same object in memory. +/// +/// Parameters: +/// +/// * `first` : The first value to compare. +/// * `second` : The second value to compare. +/// * `T` : The type parameter representing the type of values being compared. +/// +/// Returns `true` if both values refer to the same object in memory, `false` +/// otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "physical_equal" { +/// let arr1 = [1, 2, 3] +/// let arr2 = arr1 +/// let arr3 = [1, 2, 3] +/// inspect!(physical_equal(arr1, arr2), content="true") // Same object +/// inspect!(physical_equal(arr1, arr3), content="false") // Different objects with same content +/// } +/// ``` pub fn physical_equal[T](a : T, b : T) -> Bool = "%refeq" ///| +/// Aborts the program with an error message. Always causes a panic, regardless +/// of the message provided. +/// +/// Parameters: +/// +/// * `message` : A string containing the error message to be displayed when +/// aborting. +/// +/// Returns a value of type `T`. However, this function never actually returns a +/// value as it always causes a panic. +/// +/// Example: +/// +/// ```moonbit +/// test "panic abort/with_message" { +/// let x : Int = abort("Something went wrong") // specify return type as Int +/// ignore(x) +/// } +/// ``` pub fn abort[T](msg : String) -> T { ignore(msg) panic() @@ -30,74 +93,531 @@ pub fn panic[T]() -> T = "%panic" // Bool primitive ops ///| +/// Performs logical negation on a boolean value. +/// +/// Parameters: +/// +/// * `value` : The boolean value to negate. +/// +/// Returns the logical NOT of the input value: `true` if the input is `false`, +/// and `false` if the input is `true`. +/// +/// Example: +/// +/// ```moonbit +/// test "not" { +/// inspect!(not(true), content="false") +/// inspect!(not(false), content="true") +/// } +/// ``` pub fn not(x : Bool) -> Bool = "%bool_not" -///| @alert deprecated "Use `not(x)` instead" +///| +/// Performs logical negation on a boolean value. Returns `false` if the input is +/// `true`, and `true` if the input is `false`. +/// +/// DEPRECATED: Use `not(x)` instead of `x.not()`. +/// +/// Parameters: +/// +/// * `self` : The boolean value to be negated. +/// +/// Returns the logical negation of the input boolean value. +/// +/// Example: +/// +/// ```moonbit +/// test "Bool::not" { +/// let x = true +/// inspect!(not(x), content="false") +/// let y = false +/// inspect!(not(y), content="true") +/// } +/// ``` +/// +/// @alert deprecated "Use `not(x)` instead" pub fn Bool::not(self : Bool) -> Bool = "%bool_not" ///| +/// Compares two boolean values for equality. +/// +/// Parameters: +/// +/// * `self` : The first boolean value to compare. +/// * `other` : The second boolean value to compare. +/// +/// Returns `true` if both boolean values are equal (either both `true` or both +/// `false`), `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Bool::op_equal" { +/// inspect!(true == true, content="true") +/// inspect!(false == true, content="false") +/// inspect!(true == false, content="false") +/// inspect!(false == false, content="true") +/// } +/// ``` pub fn Bool::op_equal(self : Bool, other : Bool) -> Bool = "%bool_eq" ///| +/// Compares two boolean values and returns their relative order. This is a +/// deprecated method and users should use `compare` instead. +/// +/// Parameters: +/// +/// * `self` : The first boolean value to compare. +/// * `other` : The second boolean value to compare against. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` (i.e., `self` is `false` +/// and `other` is `true`) +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` (i.e., `self` is `true` +/// and `other` is `false`) +/// +/// Example: +/// +/// ```moonbit +/// test "Bool::op_compare/deprecated" { +/// let t = true +/// let f = false +/// // This usage is deprecated, use compare() instead +/// inspect!(t.compare(f), content="1") +/// inspect!(f.compare(t), content="-1") +/// inspect!(t.compare(t), content="0") +/// } +/// ``` +/// /// @alert deprecated "Use `compare` instead" /// @coverage.skip pub fn Bool::op_compare(self : Bool, other : Bool) -> Int = "%bool_compare" ///| +/// Compares two boolean values and returns their relative order. The comparison +/// follows the rule that `false` is less than `true`. +/// +/// Parameters: +/// +/// * `self` : The first boolean value to compare. +/// * `other` : The second boolean value to compare against. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is `false` and `other` is `true` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is `true` and `other` is `false` +/// +/// Example: +/// +/// ```moonbit +/// test "Bool::compare" { +/// inspect!(true.compare(false), content="1") // true > false +/// inspect!(false.compare(true), content="-1") // false < true +/// inspect!(true.compare(true), content="0") // true = true +/// } +/// ``` pub fn Bool::compare(self : Bool, other : Bool) -> Int = "%bool_compare" ///| +/// Returns the default value for the `Bool` type, which is `false`. +/// +/// Returns a `Bool` value that represents the default state of a boolean value. +/// +/// Example: +/// +/// ```moonbit +/// test "Bool::default" { +/// let b : Bool = Bool::default() +/// inspect!(b, content="false") +/// } +/// ``` pub fn Bool::default() -> Bool = "%bool_default" // int32 primitive ops ///| +/// Performs arithmetic negation on an integer value, returning its additive +/// inverse. +/// +/// Parameters: +/// +/// * `self` : The integer value to negate. +/// +/// Returns the negation of the input value. For all inputs except +/// `Int::min_value()`, returns the value with opposite sign. When the input is +/// `Int::min_value()`, returns `Int::min_value()` due to two's complement +/// representation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_neg" { +/// inspect!(-42, content="-42") +/// inspect!(42, content="42") +/// inspect!(--2147483647, content="2147483647") // negating near min value +/// } +/// ``` pub fn Int::op_neg(self : Int) -> Int = "%i32_neg" ///| +/// Adds two 32-bit signed integers. Performs two's complement arithmetic, which +/// means the operation will wrap around if the result exceeds the range of a +/// 32-bit integer. +/// +/// Parameters: +/// +/// * `self` : The first integer operand. +/// * `other` : The second integer operand. +/// +/// Returns a new integer that is the sum of the two operands. If the +/// mathematical sum exceeds the range of a 32-bit integer (-2,147,483,648 to +/// 2,147,483,647), the result wraps around according to two's complement rules. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_add" { +/// inspect!(42 + 1, content="43") +/// inspect!(2147483647 + 1, content="-2147483648") // Overflow wraps around to minimum value +/// } +/// ``` pub fn Int::op_add(self : Int, other : Int) -> Int = "%i32_add" ///| +/// Performs subtraction between two 32-bit integers, following standard two's +/// complement arithmetic rules. When the result overflows or underflows, it +/// wraps around within the 32-bit integer range. +/// +/// Parameters: +/// +/// * `self` : The minuend (the number being subtracted from). +/// * `other` : The subtrahend (the number to subtract). +/// +/// Returns the difference between `self` and `other`. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_sub" { +/// let a = 42 +/// let b = 10 +/// inspect!(a - b, content="32") +/// let max = 2147483647 // Int maximum value +/// inspect!(max - -1, content="-2147483648") // Overflow case +/// } +/// ``` pub fn Int::op_sub(self : Int, other : Int) -> Int = "%i32_sub" ///| +/// Multiplies two 32-bit integers. This is the implementation of the `*` +/// operator for `Int`. +/// +/// Parameters: +/// +/// * `self` : The first integer operand. +/// * `other` : The second integer operand. +/// +/// Returns the product of the two integers. If the result overflows the range of +/// `Int`, it wraps around according to two's complement arithmetic. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_mul" { +/// inspect!(42 * 2, content="84") +/// inspect!(-10 * 3, content="-30") +/// let max = 2147483647 // Int.max_value +/// inspect!(max * 2, content="-2") // Overflow wraps around +/// } +/// ``` pub fn Int::op_mul(self : Int, other : Int) -> Int = "%i32_mul" ///| +/// Performs integer division between two 32-bit integers. The result is +/// truncated towards zero (rounds down for positive numbers and up for negative +/// numbers). +/// +/// Parameters: +/// +/// * `dividend` : The first integer operand to be divided. +/// * `divisor` : The second integer operand that divides the dividend. +/// +/// Returns the quotient of the division operation. +/// +/// Throws a panic if `divisor` is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_div" { +/// inspect!(10 / 3, content="3") // truncates towards zero +/// inspect!(-10 / 3, content="-3") +/// inspect!(10 / -3, content="-3") +/// } +/// +/// test "panic Int::op_div/division_by_zero" { +/// ignore(42 / 0) // Panics with division by zero +/// } +/// ``` pub fn Int::op_div(self : Int, other : Int) -> Int = "%i32_div" ///| +/// Calculates the remainder of dividing one integer by another. The result +/// follows the formula `dividend - (dividend / divisor) * divisor`, maintaining +/// the same sign as the dividend. +/// +/// Parameters: +/// +/// * `self` : The dividend (the number being divided). +/// * `other` : The divisor (the number to divide by). +/// +/// Returns the remainder of the division. If `other` is 0, the behavior is +/// undefined. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_mod" { +/// inspect!(7 % 3, content="1") +/// inspect!(-7 % 3, content="-1") +/// inspect!(7 % -3, content="1") +/// } +/// +/// test "panic Int::op_mod/division_by_zero" { +/// ignore(7 % 0) // Panics with division by zero +/// } +/// ``` pub fn Int::op_mod(self : Int, other : Int) -> Int = "%i32_mod" ///| +/// Performs a bitwise NOT operation on a 32-bit integer. Flips each bit in the +/// integer's binary representation (0 becomes 1 and 1 becomes 0). +/// +/// Parameters: +/// +/// * `value` : The 32-bit integer on which to perform the bitwise NOT operation. +/// +/// Returns a new integer with all bits flipped from the input value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::lnot" { +/// let a = -1 // All bits are 1 +/// let b = 0 // All bits are 0 +/// inspect!(a.lnot(), content="0") +/// inspect!(b.lnot(), content="-1") +/// } +/// ``` pub fn Int::lnot(self : Int) -> Int = "%i32_lnot" ///| +/// Performs a bitwise AND operation between two 32-bit integers. Each bit in the +/// result is set to 1 only if the corresponding bits in both operands are 1. +/// +/// Parameters: +/// +/// * `self` : The first 32-bit integer operand. +/// * `other` : The second 32-bit integer operand. +/// +/// Returns the result of the bitwise AND operation. The resulting value has a +/// bit set to 1 at each position where both input integers have a bit set to 1. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::land" { +/// let x = 0xF0 // 11110000 +/// let y = 0xAA // 10101010 +/// inspect!(x & y, content="160") // 10100000 = 160 +/// } +/// ``` pub fn Int::land(self : Int, other : Int) -> Int = "%i32_land" ///| +/// Performs a bitwise OR operation between two 32-bit integers. For each bit +/// position, the result is 1 if at least one of the corresponding bits in either +/// operand is 1. +/// +/// Parameters: +/// +/// * `self` : The first integer operand. +/// * `other` : The second integer operand. +/// +/// Returns a new integer where each bit is set to 1 if at least one of the +/// corresponding bits in either operand is 1, and 0 otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::lor" { +/// let x = 0xF0F0 // 1111_0000_1111_0000 +/// let y = 0x0F0F // 0000_1111_0000_1111 +/// inspect!(x | y, content="65535") // 1111_1111_1111_1111 = 65535 +/// } +/// ``` pub fn Int::lor(self : Int, other : Int) -> Int = "%i32_lor" ///| +/// Performs a bitwise XOR operation between two integers. +/// +/// Parameters: +/// +/// * `self` : The first integer operand. +/// * `other` : The second integer operand. +/// +/// Returns a new integer where each bit is set to 1 if the corresponding bits in +/// the operands are different, and 0 if they are the same. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::lxor" { +/// let x = 0xF0F0 // 1111_0000_1111_0000 +/// let y = 0x0F0F // 0000_1111_0000_1111 +/// inspect!(x ^ y, content="65535") // 1111_1111_1111_1111 +/// inspect!(x ^ x, content="0") // XOR with self gives 0 +/// } +/// ``` pub fn Int::lxor(self : Int, other : Int) -> Int = "%i32_lxor" ///| +/// Performs a left shift operation on a 32-bit integer. Shifts each bit in the +/// integer to the left by the specified number of positions, filling the +/// rightmost positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The integer value to be shifted. +/// * `shift` : The number of positions to shift. Must be a non-negative value +/// less than 32. Values outside this range will be masked with `& 31`. +/// +/// Returns a new integer with bits shifted left by the specified number of +/// positions. For each position shifted, the rightmost bit is filled with 0, and +/// the leftmost bit is discarded. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_shl" { +/// let x = 1 +/// inspect!(x << 3, content="8") // Binary: 1 -> 1000 +/// let y = -4 +/// inspect!(y << 2, content="-16") // Binary: 100 -> 10000 +/// } +/// ``` pub fn Int::op_shl(self : Int, other : Int) -> Int = "%i32_shl" ///| +/// Performs an arithmetic right shift operation on an integer value. Shifts the +/// bits of the first operand to the right by the number of positions specified +/// by the second operand. The sign bit is preserved and copied to the leftmost +/// positions. +/// +/// Parameters: +/// +/// * `self` : The integer value to be shifted. +/// * `shift` : The number of positions to shift the bits to the right. Must be +/// non-negative. +/// +/// Returns an integer representing the result of the arithmetic right shift +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_shr" { +/// let n = -16 +/// inspect!(n >> 2, content="-4") // Sign bit is preserved during shift +/// let p = 16 +/// inspect!(p >> 2, content="4") // Regular right shift for positive numbers +/// } +/// ``` pub fn Int::op_shr(self : Int, other : Int) -> Int = "%i32_shr" ///| +/// Performs a left shift operation on a 32-bit integer. Shifts each bit in the +/// integer to the left by the specified number of positions, filling the vacated +/// bit positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The integer value to be shifted. +/// * `shift` : The number of positions to shift the bits to the left. +/// +/// Returns an integer containing the result of shifting `self` left by `shift` +/// positions. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::lsl" { +/// let x = 1 +/// inspect!(x << 3, content="8") // Binary: 1 -> 1000 +/// let y = 42 +/// inspect!(y << 2, content="168") // Binary: 101010 -> 10101000 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn Int::lsl(self : Int, other : Int) -> Int = "%i32_shl" ///| +/// Performs a left shift operation on a 32-bit integer. Shifts the bits of the +/// first operand to the left by the specified number of positions. The rightmost +/// positions are filled with zeros. +/// +/// Parameters: +/// +/// * `value` : The integer value to be shifted. +/// * `shift` : The number of positions to shift left. Must be non-negative and +/// less than 32. +/// +/// Returns a new integer value after performing the left shift operation. The +/// value is equal to multiplying the input by 2 raised to the power of the shift +/// count. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::shl" { +/// let x = 1 +/// inspect!(x << 3, content="8") // Equivalent to x << 3 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn Int::shl(self : Int, other : Int) -> Int = "%i32_shl" ///| +/// Performs a logical right shift operation on a signed 32-bit integer. In a +/// logical right shift, zeros are shifted in from the left, regardless of the +/// sign bit. This function is DEPRECATED and users should use `UInt` type with +/// the infix operator `>>` instead. +/// +/// Parameters: +/// +/// * `self` : The signed 32-bit integer value to be shifted. +/// * `shift` : The number of positions to shift right. Must be non-negative. +/// +/// Returns a signed 32-bit integer containing the same bits as if the input were +/// treated as an unsigned integer and shifted right logically. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::lsr" { +/// let x = -4 // Binary: 11111...11100 +/// let unsigned = x.reinterpret_as_uint() // Convert to UInt first +/// inspect!(unsigned >> 1, content="2147483646") // Using the recommended operator +/// } +/// ``` +/// /// @alert deprecated "Use UInt type and infix operator `>>` instead" /// @coverage.skip pub fn Int::lsr(self : Int, other : Int) -> Int { @@ -105,34 +625,181 @@ pub fn Int::lsr(self : Int, other : Int) -> Int { } ///| +/// Performs an arithmetic right shift operation on a 32-bit integer value, +/// preserving the sign bit by replicating it into the positions vacated by the +/// shift. This is a deprecated function; use the infix operator `>>` instead. +/// +/// Parameters: +/// +/// * `self` : The integer value to be shifted. +/// * `shift` : The number of positions to shift right. Must be non-negative. +/// +/// Returns a new integer value that is the result of arithmetically shifting +/// `self` right by `shift` positions. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::asr" { +/// let x = -16 +/// inspect!(x >> 2, content="-4") // Right shift preserves sign bit +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip pub fn Int::asr(self : Int, other : Int) -> Int = "%i32_shr" ///| +/// Performs an arithmetic right shift operation on a 32-bit integer by the +/// specified number of positions. The operation preserves the sign bit, +/// replicating it into the positions vacated by the shift. +/// +/// Parameters: +/// +/// * `self` : The integer value to be shifted. +/// * `shift` : The number of positions to shift right. +/// +/// Returns a new integer representing the result of shifting `self` right by +/// `shift` positions. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::shr" { +/// let n = -1024 +/// inspect!(n >> 3, content="-128") // Preserves sign bit during right shift +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip + pub fn Int::shr(self : Int, other : Int) -> Int = "%i32_shr" ///| +/// Counts the number of consecutive zero bits at the least significant end of +/// the integer's binary representation. +/// +/// Parameters: +/// +/// * `self` : The integer value whose trailing zeros are to be counted. +/// +/// Returns the number of trailing zero bits (0 to 32). For example, returns 0 if +/// the value is odd (least significant bit is 1), returns 32 if the value is 0 +/// (all bits are zeros). +/// +/// Example: +/// +/// ```moonbit +/// test "Int::ctz" { +/// let x = 0 +/// inspect!(x.ctz(), content="32") // All bits are zero +/// let y = 1 +/// inspect!(y.ctz(), content="0") // No trailing zeros +/// let z = 16 +/// inspect!(z.ctz(), content="4") // Binary: ...10000 +/// } +/// ``` pub fn Int::ctz(self : Int) -> Int = "%i32_ctz" ///| pub fn Int::clz(self : Int) -> Int = "%i32_clz" ///| +/// Counts the number of set bits (1s) in the binary representation of a 32-bit +/// integer. +/// +/// Parameters: +/// +/// * `self` : The 32-bit integer whose bits are to be counted. +/// +/// Returns the number of bits set to 1 in the binary representation of the input +/// integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::popcnt" { +/// let x = 0b1011 // Binary: 1011 (3 bits set) +/// inspect!(x.popcnt(), content="3") +/// let y = -1 // All bits set in two's complement +/// inspect!(y.popcnt(), content="32") +/// } +/// ``` pub fn Int::popcnt(self : Int) -> Int = "%i32_popcnt" ///| +/// Compares two integers for equality. +/// +/// Parameters: +/// +/// * `self` : The first integer to compare. +/// * `other` : The second integer to compare. +/// +/// Returns `true` if both integers have the same value, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::op_equal" { +/// inspect!(42 == 42, content="true") +/// inspect!(42 == -42, content="false") +/// } +/// ``` pub fn Int::op_equal(self : Int, other : Int) -> Bool = "%i32_eq" ///| +/// Compares two integers and returns their relative order. +/// +/// Parameters: +/// +/// * `self` : The first integer to compare. +/// * `other` : The second integer to compare against. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "Int::compare" { +/// let a = 42 +/// let b = 24 +/// inspect!(a.compare(b), content="1") // 42 > 24 +/// inspect!(b.compare(a), content="-1") // 24 < 42 +/// inspect!(a.compare(a), content="0") // 42 = 42 +/// } +/// ``` pub fn Int::compare(self : Int, other : Int) -> Int = "%i32_compare" ///| pub fn Int::is_pos(self : Int) -> Bool = "%i32_is_pos" ///| +/// Tests whether an integer is negative. +/// +/// Parameters: +/// +/// * `self` : The integer to test. +/// +/// Returns `true` if the integer is negative, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::is_neg" { +/// let neg = -42 +/// let zero = 0 +/// let pos = 42 +/// inspect!(neg.is_neg(), content="true") +/// inspect!(zero.is_neg(), content="false") +/// inspect!(pos.is_neg(), content="false") +/// } +/// ``` pub fn Int::is_neg(self : Int) -> Bool = "%i32_is_neg" ///| @@ -142,12 +809,64 @@ pub fn Int::is_non_pos(self : Int) -> Bool = "%i32_is_non_pos" pub fn Int::is_non_neg(self : Int) -> Bool = "%i32_is_non_neg" ///| +/// Returns the default value for integers, which is 0. +/// +/// Returns an integer value of 0. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::default" { +/// let x : Int = Int::default() +/// inspect!(x, content="0") +/// } +/// ``` pub fn Int::default() -> Int = "%i32_default" ///| +/// Converts a 32-bit integer to a double-precision floating-point number. The +/// conversion preserves the exact value since all integers in the range of `Int` +/// can be represented exactly as `Double` values. +/// +/// Parameters: +/// +/// * `self` : The 32-bit integer to be converted. +/// +/// Returns a double-precision floating-point number that represents the same +/// numerical value as the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_double" { +/// let n = 42 +/// inspect!(n.to_double(), content="42") +/// let neg = -42 +/// inspect!(neg.to_double(), content="-42") +/// } +/// ``` + pub fn Int::to_double(self : Int) -> Double = "%i32_to_f64" ///| +/// Converts a double-precision floating-point number to an unsigned 32-bit +/// integer by truncating the decimal part. When the input is NaN or negative, +/// returns 0. When the input exceeds the maximum value of UInt (4294967295), +/// returns 4294967295. +/// +/// Parameters: +/// +/// * `value` : The double-precision floating-point number to be converted. +/// +/// Returns an unsigned 32-bit integer representing the truncated value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::trunc_double" { +/// inspect!(UInt::trunc_double(42.75), content="42") +/// } +/// ``` pub fn UInt::trunc_double(val : Double) -> UInt = "%f64.to_u32" ///| @@ -158,103 +877,681 @@ pub fn UInt::trunc_double(val : Double) -> UInt = "%f64.to_u32" pub fn Int::reinterpret_as_uint(self : Int) -> UInt = "%i32.to_u32_reinterpret" ///| +/// Reinterprets a signed 32-bit integer as an unsigned 32-bit integer. For +/// numbers within the range \[0, 2^31-1], the value remains the same. For +/// negative numbers, they are reinterpreted as large positive numbers in the +/// range \[2^31, 2^32-1]. +/// +/// Parameters: +/// +/// * `value` : The signed 32-bit integer to be reinterpreted. +/// +/// Returns an unsigned 32-bit integer that has the same bit pattern as the +/// input. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_uint" { +/// let pos = 42 +/// let neg = -1 +/// inspect!(pos.reinterpret_as_uint(), content="42") +/// inspect!(neg.reinterpret_as_uint(), content="4294967295") // 2^32 - 1 +/// } +/// ``` +/// /// @alert deprecated "Use `reinterpret_as_uint` instead" /// @coverage.skip pub fn Int::to_uint(self : Int) -> UInt = "%i32.to_u32_reinterpret" // Double primitive ops ///| +/// Converts a 32-bit signed integer to an unsigned 64-bit integer by first +/// converting it to a signed 64-bit integer and then reinterpreting the bits as +/// an unsigned value. +/// +/// Parameters: +/// +/// * `value` : The 32-bit signed integer to be converted. +/// +/// Returns an unsigned 64-bit integer representing the same bit pattern as the +/// input value when extended to 64 bits. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_uint64" { +/// let pos = 42 +/// inspect!(pos.to_uint64(), content="42") +/// let neg = -1 +/// inspect!(neg.to_uint64(), content="18446744073709551615") // 2^64 - 1 +/// } +/// ``` + pub fn Int::to_uint64(self : Int) -> UInt64 { self.to_int64().reinterpret_as_uint64() } ///| +/// Negates a double-precision floating-point number. For non-NaN inputs, changes +/// the sign of the number. For NaN inputs, returns NaN. +/// +/// Parameters: +/// +/// * `number` : The double-precision floating-point number to negate. +/// +/// Returns a new double-precision floating-point number that is the negation of +/// the input number. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_neg" { +/// inspect!(-42.0, content="-42") +/// inspect!(--42.0, content="42") +/// inspect!(-(0.0 / 0.0), content="NaN") // Negating NaN returns NaN +/// } +/// ``` pub fn Double::op_neg(self : Double) -> Double = "%f64_neg" ///| +/// Adds two double-precision floating-point numbers together following IEEE 754 +/// standards. +/// +/// Parameters: +/// +/// * `self` : The first double-precision floating-point number. +/// * `other` : The second double-precision floating-point number to add. +/// +/// Returns the sum of the two numbers. Special cases follow IEEE 754 rules: +/// +/// * If either operand is NaN, returns NaN +/// * If adding +∞ and -∞, returns NaN +/// * If adding ±∞ with any finite number, returns ±∞ +/// * If adding +0.0 and -0.0, returns +0.0 +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_add" { +/// inspect!(2.5 + 3.7, content="6.2") +/// inspect!(1.0 / 0.0 + -1.0 / 0.0, content="NaN") // Infinity + -Infinity = NaN +/// } +/// ``` pub fn Double::op_add(self : Double, other : Double) -> Double = "%f64_add" ///| +/// Performs subtraction between two double-precision floating-point numbers. +/// +/// Parameters: +/// +/// * `self` : The first operand (minuend). +/// * `other` : The second operand (subtrahend). +/// +/// Returns the difference between the two numbers according to IEEE 754 +/// double-precision arithmetic rules. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_sub" { +/// let a = 5.0 +/// let b = 3.0 +/// inspect!(a - b, content="2") +/// inspect!(0.0 / 0.0 - 1.0, content="NaN") // NaN - anything = NaN +/// } +/// ``` pub fn Double::op_sub(self : Double, other : Double) -> Double = "%f64_sub" ///| +/// Multiplies two double-precision floating-point numbers. This is the +/// implementation of the `*` operator for `Double` type. +/// +/// Parameters: +/// +/// * `self` : The first double-precision floating-point operand. +/// * `other` : The second double-precision floating-point operand. +/// +/// Returns a new double-precision floating-point number representing the product +/// of the two operands. Special cases follow IEEE 754 standard: +/// +/// * If either operand is NaN, returns NaN +/// * If one operand is infinity and the other is zero, returns NaN +/// * If one operand is infinity and the other is a non-zero finite number, +/// returns infinity with the appropriate sign +/// * If both operands are infinity, returns infinity with the appropriate sign +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_mul" { +/// inspect!(2.5 * 2.0, content="5") +/// inspect!(-2.0 * 3.0, content="-6") +/// let nan = 0.0 / 0.0 // NaN +/// inspect!(nan * 1.0, content="NaN") +/// } +/// ``` pub fn Double::op_mul(self : Double, other : Double) -> Double = "%f64_mul" ///| +/// Performs division between two double-precision floating-point numbers. +/// Follows IEEE 754 standard for floating-point arithmetic, including handling +/// of special cases like division by zero (returns infinity) and operations +/// involving NaN. +/// +/// Parameters: +/// +/// * `self` : The dividend (numerator) in the division operation. +/// * `other` : The divisor (denominator) in the division operation. +/// +/// Returns the result of dividing `self` by `other`. Special cases follow IEEE +/// 754: +/// +/// * Division by zero returns positive or negative infinity based on the +/// dividend's sign +/// * Operations involving NaN return NaN +/// * Division of infinity by infinity returns NaN +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_div" { +/// inspect!(6.0 / 2.0, content="3") +/// inspect!(-6.0 / 2.0, content="-3") +/// inspect!(1.0 / 0.0, content="Infinity") +/// } +/// ``` pub fn Double::op_div(self : Double, other : Double) -> Double = "%f64_div" ///| +/// Calculates the square root of a double-precision floating-point number. For +/// non-negative numbers, returns the positive square root. For negative numbers +/// or NaN, returns NaN. +/// +/// Parameters: +/// +/// * `self` : The double-precision floating-point number whose square root is to +/// be calculated. +/// +/// Returns the square root of the input number, or NaN if the input is negative +/// or NaN. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::sqrt" { +/// inspect!(4.0.sqrt(), content="2") +/// inspect!(0.0.sqrt(), content="0") +/// inspect!((-1.0).sqrt(), content="NaN") +/// } +/// ``` pub fn Double::sqrt(self : Double) -> Double = "%f64_sqrt" ///| +/// Compares two double-precision floating-point numbers for equality following +/// IEEE 754 rules. Returns `true` if both numbers are equal, including when both +/// are `NaN`. Note that this differs from the standard IEEE 754 behavior where +/// `NaN` is not equal to any value, including itself. +/// +/// Parameters: +/// +/// * `self` : The first double-precision floating-point number to compare. +/// * `other` : The second double-precision floating-point number to compare. +/// +/// Returns `true` if both numbers are equal, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_equal" { +/// let a = 3.14 +/// let b = 3.14 +/// let c = 2.718 +/// inspect!(a == b, content="true") +/// inspect!(a == c, content="false") +/// let nan = 0.0 / 0.0 // NaN +/// inspect!(nan == nan, content="false") // Note: NaN equals itself in MoonBit +/// } +/// ``` pub fn Double::op_equal(self : Double, other : Double) -> Bool = "%f64_eq" ///| +/// Tests for inequality between two double-precision floating-point numbers. +/// Takes into account special cases like NaN, where two NaN values are +/// considered not equal to each other. +/// +/// Parameters: +/// +/// * `self` : The first double-precision floating-point number to compare. +/// * `other` : The second double-precision floating-point number to compare. +/// +/// Returns `true` if the two numbers are not equal according to IEEE 754 rules, +/// `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::op_neq" { +/// inspect!(1.0 != 2.0, content="true") +/// inspect!(1.0 != 1.0, content="false") +/// inspect!(0.0 / 0.0 != 0.0 / 0.0, content="true") // NaN != NaN +/// } +/// ``` pub fn Double::op_neq(self : Double, other : Double) -> Bool = "%f64_ne" ///| +/// Compares two double-precision floating-point numbers and returns their +/// relative order. Follows IEEE 754 rules for floating-point comparisons, +/// including handling of special values like NaN. +/// +/// Parameters: +/// +/// * `self` : The first double-precision floating-point number to compare. +/// * `other` : The second double-precision floating-point number to compare +/// against. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// * If either value is NaN, returns an implementation-defined value that is +/// consistent with total ordering +/// +/// Example: +/// +/// ```moonbit +/// test "Double::compare" { +/// let a = 3.14 +/// let b = 2.718 +/// inspect!(a.compare(b), content="1") // 3.14 > 2.718 +/// inspect!(b.compare(a), content="-1") // 2.718 < 3.14 +/// inspect!(a.compare(a), content="0") // 3.14 = 3.14 +/// } +/// ``` pub fn Double::compare(self : Double, other : Double) -> Int = "%f64_compare" ///| +/// Returns the default value for double-precision floating-point numbers (0.0). +/// +/// Returns a `Double` value initialized to 0.0. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::default" { +/// inspect!(Double::default(), content="0") +/// } +/// ``` pub fn Double::default() -> Double = "%f64_default" ///| fn Double::to_unchecked_int(self : Double) -> Int = "%f64_to_i32" ///| +/// Converts an unsigned 32-bit integer to a double-precision floating-point +/// number. Since the range of unsigned 32-bit integers is smaller than what can +/// be precisely represented by a double-precision floating-point number, this +/// conversion is guaranteed to be exact. +/// +/// Parameters: +/// +/// * `value` : The unsigned 32-bit integer to be converted. +/// +/// Returns a double-precision floating-point number that exactly represents the +/// input value. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::convert_uint" { +/// let n = 42U +/// inspect!(Double::convert_uint(n), content="42") +/// let max = 4294967295U // maximum value of UInt +/// inspect!(Double::convert_uint(max), content="4294967295") +/// } +/// ``` pub fn Double::convert_uint(val : UInt) -> Double = "%u32.to_f64" // Char primitive ops ///| +/// Converts a character to its Unicode code point value as an integer. +/// +/// Parameters: +/// +/// * `self` : The character to be converted. +/// +/// Returns an integer representing the Unicode code point value of the +/// character. +/// +/// Example: +/// +/// ```moonbit +/// test "Char::to_int" { +/// inspect!('A'.to_int(), content="65") // ASCII value of 'A' +/// inspect!('あ'.to_int(), content="12354") // Unicode code point of 'あ' +/// } +/// ``` pub fn Char::to_int(self : Char) -> Int = "%char_to_int" ///| +/// Converts a Unicode character to its unsigned 32-bit integer code point +/// representation. The character's code point value is first converted to a +/// signed integer and then reinterpreted as an unsigned integer. +/// +/// Parameters: +/// +/// * `character` : The Unicode character to be converted. +/// +/// Returns an unsigned 32-bit integer representing the character's Unicode code +/// point. +/// +/// Example: +/// +/// ```moonbit +/// test "Char::to_uint" { +/// let c = 'A' +/// inspect!(c.to_uint(), content="65") // ASCII value of 'A' +/// let emoji = '🤣' +/// inspect!(emoji.to_uint(), content="129315") // Unicode code point U+1F923 +/// } +/// ``` pub fn Char::to_uint(self : Char) -> UInt { self.to_int().reinterpret_as_uint() } ///| +/// pub fn Char::from_int(val : Int) -> Char = "%char_from_int" ///| +/// Compares two characters for equality. +/// +/// Parameters: +/// +/// * `self` : The first character to compare. +/// * `other` : The second character to compare. +/// +/// Returns `true` if both characters represent the same Unicode code point, +/// `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "Char::op_equal" { +/// let a = 'A' +/// let b = 'A' +/// let c = 'B' +/// inspect!(a == b, content="true") +/// inspect!(a == c, content="false") +/// } +/// ``` pub fn Char::op_equal(self : Char, other : Char) -> Bool = "%char_eq" ///| +/// Compares two characters based on their Unicode code points. Returns a +/// negative value if the first character comes before the second, zero if they +/// are equal, and a positive value if the first character comes after the +/// second. +/// +/// Parameters: +/// +/// * `self` : The first character to compare. +/// * `other` : The second character to compare against. +/// +/// Returns an integer indicating the relative ordering: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "Char::compare" { +/// inspect!('a'.compare('b'), content="-1") +/// inspect!('b'.compare('a'), content="1") +/// inspect!('a'.compare('a'), content="0") +/// } +/// ``` pub fn Char::compare(self : Char, other : Char) -> Int = "%char_compare" ///| +/// Returns the default value for the `Char` type, which is the null character +/// (`'\x00'`). +/// +/// Returns a `Char` value representing the null character. +/// +/// Example: +/// +/// ```moonbit +/// test "Char::default" { +/// inspect!(Char::default(), content="'\\x00'") +/// } +/// ``` pub fn Char::default() -> Char = "%char_default" // Bytes primitive ops ///| +/// Retrieves a byte at the specified index from a byte sequence. +/// +/// Parameters: +/// +/// * `bytes` : The byte sequence to access. +/// * `index` : The position in the byte sequence from which to retrieve the +/// byte. +/// +/// Returns a byte value from the specified position in the sequence. +/// +/// Throws a panic if the index is negative or greater than or equal to the +/// length of the byte sequence. +/// +/// Example: +/// +/// ```moonbit +/// test "Bytes::op_get" { +/// let bytes = b"\x01\x02\x03" +/// inspect!(bytes[1], content="b'\\x02'") +/// } +/// +/// test "panic Bytes::op_get/out_of_bounds" { +/// let bytes = b"\x01\x02\x03" +/// ignore(bytes[3]) // Index out of bounds +/// } +/// ``` + pub fn Bytes::op_get(self : Bytes, idx : Int) -> Byte = "%bytes_get" ///| +/// Retrieves a byte at the specified index from a byte sequence without +/// performing bounds checking. This is a low-level operation that should be used +/// with caution. +/// +/// Parameters: +/// +/// * `bytes` : The byte sequence to retrieve the byte from. +/// * `index` : The position in the byte sequence from which to retrieve the +/// byte. +/// +/// Returns a single byte from the specified position in the byte sequence. +/// +/// Throws a panic if the index is negative or greater than or equal to the +/// length of the byte sequence. +/// +/// Example: +/// +/// ```moonbit +/// test "Bytes::unsafe_get" { +/// let bytes = b"\x01\x02\x03" +/// inspect!(bytes.unsafe_get(1), content="b'\\x02'") +/// } +/// +/// test "panic Bytes::unsafe_get/out_of_bounds" { +/// let bytes = b"\x01\x02\x03" +/// ignore(bytes.unsafe_get(3)) // Index out of bounds +/// } +/// ``` +/// /// @alert unsafe "Panic if index is out of bounds" pub fn Bytes::unsafe_get(self : Bytes, idx : Int) -> Byte = "%bytes_get" ///| +/// Sets the byte value at the specified index in a byte sequence. +/// +/// Parameters: +/// +/// * `bytes` : The byte sequence to modify. +/// * `index` : The position in the byte sequence where the value will be set. +/// * `value` : The byte value to be set at the specified index. +/// +/// Throws a runtime error if `index` is out of bounds (less than 0 or greater +/// than or equal to the length of the byte sequence). +/// +/// Example: +/// +/// ```moonbit +/// test "Bytes::op_set" { +/// let arr = FixedArray::make(3, b'\x00') +/// let _ = arr.op_set(1, b'\xFF') +/// inspect!(arr, content="[b'\\x00', b'\\xFF', b'\\x00']") +/// } +/// +/// test "panic Bytes::op_set/out_of_bounds" { +/// let arr = FixedArray::make(3, b'\x00') +/// ignore(arr.op_set(3, b'\xFF')) // Index out of bounds +/// } +/// ``` +/// /// @alert deprecated "Bytes is about to be changed to immutable, use `FixedArray[Byte]` instead" pub fn Bytes::op_set(self : Bytes, idx : Int, val : Byte) -> Unit = "%bytes_set" ///| +/// Returns the number of bytes in a byte sequence. +/// +/// Parameters: +/// +/// * `bytes` : The byte sequence whose length is to be determined. +/// +/// Returns an integer representing the length (number of bytes) of the sequence. +/// +/// Example: +/// +/// ```moonbit +/// test "Bytes::length" { +/// let bytes = b"\x01\x02\x03" +/// inspect!(bytes.length(), content="3") +/// let empty = b"" +/// inspect!(empty.length(), content="0") +/// } +/// ``` pub fn Bytes::length(self : Bytes) -> Int = "%bytes_length" ///| +/// Creates a new byte sequence of the specified length, where each byte is +/// initialized to the given value. +/// +/// Parameters: +/// +/// * `length` : The length of the byte sequence to create. Must be non-negative. +/// * `initial_value` : The byte value used to initialize each position in the +/// sequence. +/// +/// Returns a new byte sequence of the specified length with all positions +/// initialized to the given value. +/// +/// Throws a panic if `length` is negative. +/// +/// Example: +/// +/// ```moonbit +/// test "Bytes::make" { +/// let bytes = Bytes::make(3, b'\xFF') +/// inspect!(bytes, content= +/// #|b"\xff\xff\xff" +/// ) +/// let empty = Bytes::make(0, b'\x00') +/// inspect!(empty, content="b\"\"") +/// } +/// +/// test "panic Bytes::make/negative_length" { +/// ignore(Bytes::make(-1, b'\x00')) // Panics: negative length +/// } +/// ``` + pub fn Bytes::make(len : Int, init : Byte) -> Bytes = "%bytes_make" ///| -/// The init value of Bytes is 0. +/// Creates a new byte sequence filled with zero bytes. +/// +/// Parameters: +/// +/// * `length` : The length of the byte sequence to create. Must be a +/// non-negative integer. +/// +/// Returns a new byte sequence of the specified length, with all bytes +/// initialized to zero. +/// +/// Example: +/// +/// ```moonbit +/// test "Bytes::new" { +/// let bytes = Bytes::new(3) +/// inspect!(bytes, content="b\"\\x00\\x00\\x00\"") +/// } +/// +/// test "Bytes::new/empty" { +/// let bytes = Bytes::new(0) +/// inspect!(bytes, content="b\"\"") +/// } +/// ``` + pub fn Bytes::new(len : Int) -> Bytes { Bytes::make(len, b'\x00') } ///| +/// Converts a 32-bit signed integer to a byte by taking its least significant 8 +/// bits. Any bits beyond the first 8 bits are truncated. +/// +/// Parameters: +/// +/// * `value` : The 32-bit signed integer to be converted. Only the least +/// significant 8 bits will be used. +/// +/// Returns a byte containing the least significant 8 bits of the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_byte" { +/// let n = 258 // In binary: 100000010 +/// inspect!(n.to_byte(), content="b'\\x02'") // Only keeps 00000010 +/// let neg = -1 // In binary: all 1's +/// inspect!(neg.to_byte(), content="b'\\xFF'") // Only keeps 11111111 +/// } +/// ``` pub fn Int::to_byte(self : Int) -> Byte = "%i32_to_byte" ///| +/// Converts an unsigned 64-bit integer to a byte by truncating it to fit within +/// the byte range (0 to 255). +/// +/// Parameters: +/// +/// * `self` : The unsigned 64-bit integer to be converted. +/// +/// Returns a byte containing the least significant 8 bits of the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt64::to_byte" { +/// let n = 258UL // In binary: 100000010 +/// inspect!(n.to_byte(), content="b'\\x02'") // Only keeps 00000010 +/// } +/// ``` pub fn UInt64::to_byte(self : UInt64) -> Byte { self.to_int().to_byte() } @@ -262,51 +1559,408 @@ pub fn UInt64::to_byte(self : UInt64) -> Byte { // FixedArray primitive ops ///| +/// Retrieves an element at the specified index from a fixed-size array. This +/// function implements the array indexing operator `[]`. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array to access. +/// * `index` : The position in the array from which to retrieve the element. +/// +/// Returns the element at the specified index. +/// +/// Throws a runtime error if the index is out of bounds (negative or greater +/// than or equal to the length of the array). +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::op_get" { +/// let arr = FixedArray::make(3, 42) +/// inspect!(arr[1], content="42") +/// } +/// +/// test "panic FixedArray::op_get/out_of_bounds" { +/// let arr = FixedArray::make(3, 0) +/// ignore(arr[3]) // Index out of bounds +/// } +/// ``` + pub fn FixedArray::op_get[T](self : FixedArray[T], idx : Int) -> T = "%fixedarray.get" ///| +/// Retrieves an element from a fixed-size array at the specified index without +/// performing bounds checking. This is an unsafe operation that may cause +/// undefined behavior if used incorrectly. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array to retrieve the element from. +/// * `index` : The position in the array from which to retrieve the element. +/// +/// Returns the element at the specified index in the array. +/// +/// Throws a panic if the index is out of bounds (negative or greater than or +/// equal to the array's length). +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::unsafe_get" { +/// let arr = FixedArray::make(3, 42) +/// inspect!(arr.unsafe_get(1), content="42") +/// } +/// +/// test "panic FixedArray::unsafe_get/out_of_bounds" { +/// let arr = FixedArray::make(3, 42) +/// ignore(arr.unsafe_get(3)) // Index out of bounds +/// } +/// ``` +/// /// @alert unsafe "Panic if index is out of bounds" pub fn FixedArray::unsafe_get[T](self : FixedArray[T], idx : Int) -> T = "%fixedarray.unsafe_get" ///| +/// Retrieves an element at the specified index from a fixed-size array. This +/// function is similar to `op_get` but provides explicit bounds checking. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array to access. +/// * `index` : The position in the array from which to retrieve the element. +/// +/// Returns the element at the specified index. +/// +/// Throws a runtime error if the index is out of bounds (less than 0 or greater +/// than or equal to the length of the array). +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::get" { +/// let arr = [1, 2, 3] +/// inspect!(arr.get(1), content="Some(2)") +/// } +/// +/// test "FixedArray::get/out_of_bounds" { +/// let arr = [1, 2, 3] +/// inspect(arr.get(3), content="None") +/// } +/// ``` pub fn FixedArray::get[T](self : FixedArray[T], idx : Int) -> T = "%fixedarray.get" ///| +/// Sets a value at the specified index in a fixed-size array. The original value +/// at that index is overwritten. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array to modify. +/// * `index` : The position in the array where the value will be set. +/// * `value` : The new value to assign at the specified index. +/// +/// Throws a runtime error if the index is out of bounds (less than 0 or greater +/// than or equal to the length of the array). +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::op_set" { +/// let arr = [1, 2, 3] +/// arr[1] = 42 +/// inspect!(arr, content="[1, 42, 3]") +/// } +/// +/// test "panic FixedArray::op_set/out_of_bounds" { +/// let arr = [1, 2, 3] +/// arr[3] = 42 // Index out of bounds +/// } +/// ``` +/// +/// @alert unsafe "Panic if index is out of bounds." +/// @intrinsic %fixedarray.set pub fn FixedArray::op_set[T](self : FixedArray[T], idx : Int, val : T) -> Unit = "%fixedarray.set" ///| +/// Sets the value at the specified index in a fixed-size array. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array to be modified. +/// * `index` : The index at which to set the value. Must be non-negative and +/// less than the array's length. +/// * `value` : The value to be set at the specified index. +/// +/// Throws a runtime error if the index is out of bounds (less than 0 or greater +/// than or equal to the array's length). +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::set" { +/// let arr = FixedArray::make(3, 0) +/// arr.set(1, 42) +/// inspect!(arr[1], content="42") +/// } +/// +/// test "panic FixedArray::set/out_of_bounds" { +/// let arr = FixedArray::make(3, 0) +/// ignore(arr.set(3, 42)) // Panic: index out of bounds +/// } +/// ``` + pub fn FixedArray::set[T](self : FixedArray[T], idx : Int, val : T) -> Unit = "%fixedarray.set" ///| +/// Returns the number of elements in a fixed-size array. +/// +/// Parameters: +/// +/// * `array` : The fixed-size array whose length is to be determined. +/// +/// Returns an integer representing the number of elements in the array. +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::length" { +/// let arr = FixedArray::make(3, 42) +/// inspect!(arr.length(), content="3") +/// } +/// ``` pub fn FixedArray::length[T](self : FixedArray[T]) -> Int = "%fixedarray.length" ///| +/// Creates a new fixed-size array with the specified length, initializing all +/// elements with the given value. +/// +/// Parameters: +/// +/// * `length` : The length of the array to create. Must be non-negative. +/// * `initial_value` : The value used to initialize all elements in the array. +/// +/// Returns a new fixed-size array of type `FixedArray[T]` with `length` +/// elements, where each element is initialized to `initial_value`. +/// +/// Throws a panic if `length` is negative. +/// +/// Example: +/// +/// ```moonbit +/// test "FixedArray::make" { +/// let arr = FixedArray::make(3, 42) +/// inspect!(arr[0], content="42") +/// inspect!(arr.length(), content="3") +/// } +/// +/// test "panic FixedArray::make/negative_length" { +/// ignore(FixedArray::make(-1, 0)) +/// } +/// ``` pub fn FixedArray::make[T](len : Int, init : T) -> FixedArray[T] = "%fixedarray.make" // String primitive ops ///| +/// Returns the number of UTF-16 code units in the string. Note that this is not +/// necessarily equal to the number of Unicode characters (code points) in the +/// string, as some characters may be represented by multiple UTF-16 code units. +/// +/// Parameters: +/// +/// * `string` : The string whose length is to be determined. +/// +/// Returns the number of UTF-16 code units in the string. +/// +/// Example: +/// +/// ```moonbit +/// test "String::length" { +/// inspect!("hello".length(), content="5") +/// inspect!("🤣".length(), content="2") // Emoji uses two UTF-16 code units +/// inspect!("".length(), content="0") // Empty string +/// } +/// ``` pub fn String::length(self : String) -> Int = "%string_length" ///| +/// Returns the length of the string in UTF-16 code units. This corresponds to +/// the number of 16-bit elements needed to store the string's contents. +/// +/// Parameters: +/// +/// * `string` : The string whose length is to be determined. +/// +/// Returns the number of UTF-16 code units in the string. Note that this may not +/// equal the number of Unicode characters (code points) in the string, as some +/// characters (like emojis) require two UTF-16 code units. +/// +/// Example: +/// +/// ```moonbit +/// test "String::charcode_length" { +/// let s = "Hello🤣" +/// inspect!(s.charcode_length(), content="7") // 5 ASCII chars + 2 surrogate pairs for emoji +/// } +/// ``` pub fn String::charcode_length(self : String) -> Int = "%string_length" ///| +/// Retrieves the character at the specified index in a string. Each character in +/// the string is represented as a UTF-16 code unit. +/// +/// Parameters: +/// +/// * `string` : The string from which to retrieve the character. +/// * `index` : The position in the string from which to retrieve the character. +/// +/// Returns the character at the specified index. +/// +/// Throws a runtime error if `index` is negative or greater than or equal to the +/// length of the string. +/// +/// Example: +/// +/// ```moonbit +/// test "String::op_get" { +/// let s = "Hello, 世界!" +/// inspect!(s[0], content="'H'") +/// inspect!(s[7], content="'世'") +/// } +/// +/// test "panic String::op_get/out_of_bounds" { +/// let s = "Hello" +/// ignore(s[5]) // Index out of bounds +/// } +/// ``` +/// +/// @alert unsafe "Panic if index is out of bounds" +/// @intrinsic %string\_get pub fn String::op_get(self : String, idx : Int) -> Char = "%string_get" ///| +/// Retrieves the character at the specified index in a string. +/// +/// Parameters: +/// +/// * `string` : The string to access. +/// * `index` : The position in the string from which to retrieve the character. +/// +/// Returns a Unicode character at the specified position in the string. +/// +/// Throws a runtime error if the index is negative or greater than or equal to +/// the length of the string. +/// +/// Example: +/// +/// ```moonbit +/// test "String::get" { +/// let s = "Hello, 世界" +/// inspect!(s.get(0), content="'H'") +/// inspect!(s.get(7), content="'世'") +/// } +/// +/// test "panic String::get/out_of_bounds" { +/// let s = "Hello" +/// ignore(s.get(-1)) // Negative index +/// ignore(s.get(5)) // Index equals length +/// } +/// ``` pub fn String::get(self : String, idx : Int) -> Char = "%string_get" ///| +/// Returns the UTF-16 code unit at a given position in the string without +/// performing bounds checking. This is a low-level function that provides direct +/// access to the internal representation of the string. +/// +/// Parameters: +/// +/// * `string` : The string from which to retrieve the code unit. +/// * `index` : The position of the code unit to retrieve. +/// +/// Returns the UTF-16 code unit at the specified position as an integer. +/// +/// Example: +/// +/// ```moonbit +/// test "String::unsafe_charcode_at" { +/// let s = "Hello🤣" +/// inspect!(s.unsafe_charcode_at(0), content="72") // 'H' +/// inspect!(s.unsafe_charcode_at(5), content="55358") // First surrogate of 🤣 +/// inspect!(s.unsafe_charcode_at(6), content="56611") // Second surrogate of 🤣 +/// } +/// ``` +/// +/// @alert unsafe "Panic if index is out of bounds." +/// @intrinsic %string\_get + pub fn String::unsafe_charcode_at(self : String, idx : Int) -> Int = "%string_get" ///| +/// Concatenates two strings, creating a new string that contains all characters +/// from the first string followed by all characters from the second string. +/// +/// Parameters: +/// +/// * `self` : The first string to concatenate. +/// * `other` : The second string to concatenate. +/// +/// Returns a new string containing the concatenation of both input strings. +/// +/// Example: +/// +/// ```moonbit +/// test "String::op_add" { +/// let hello = "Hello" +/// let world = " World!" +/// inspect!(hello + world, content="Hello World!") +/// inspect!("" + "abc", content="abc") // concatenating with empty string +/// } +/// ``` pub fn String::op_add(self : String, other : String) -> String = "%string_add" ///| +/// Tests whether two strings are equal by comparing their characters. +/// +/// Parameters: +/// +/// * `self` : The first string to compare. +/// * `other` : The second string to compare. +/// +/// Returns `true` if both strings contain exactly the same sequence of +/// characters, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "String::op_equal" { +/// let str1 = "hello" +/// let str2 = "hello" +/// let str3 = "world" +/// inspect!(str1 == str2, content="true") +/// inspect!(str1 == str3, content="false") +/// } +/// ``` pub fn String::op_equal(self : String, other : String) -> Bool = "%string_eq" ///| +/// Returns the string itself without any modifications. This method is primarily +/// used to implement the `Show` trait, which requires a `to_string` function. +/// +/// Parameters: +/// +/// * `string` : The string value to be returned. +/// +/// Returns the same string that was passed in. +/// +/// Example: +/// +/// ```moonbit +/// test "String::to_string" { +/// let s = "hello" +/// inspect!(s.to_string(), content="hello") +/// } +/// ``` pub fn String::to_string(self : String) -> String = "%string_to_string" ///| @@ -314,10 +1968,48 @@ pub fn String::to_string(self : String) -> String = "%string_to_string" priv type UnsafeMaybeUninit[_] ///| -// Byte primitive +/// Converts a byte value to a 32-bit signed integer. The resulting integer will +/// have the same binary representation as the byte value, preserving the +/// numerical value in the range \[0, 255]. +/// +/// Parameters: +/// +/// * `byte` : The byte value to be converted to an integer. +/// +/// Returns a 32-bit signed integer representing the same numerical value as the +/// input byte. +/// +/// Example: +/// +/// ```moonbit +/// test "Byte::to_int" { +/// let b = b'\xFF' // byte with value 255 +/// inspect!(b.to_int(), content="255") +/// let zero = b'\x00' +/// inspect!(zero.to_int(), content="0") +/// } +/// ``` pub fn Byte::to_int(self : Byte) -> Int = "%byte_to_int" ///| +/// Converts a byte value to a 64-bit signed integer by first converting it to a +/// 32-bit integer and then extending it to a 64-bit integer. +/// +/// Parameters: +/// +/// * `byte` : The byte value to be converted. +/// +/// Returns a 64-bit signed integer representing the same numerical value as the +/// input byte. +/// +/// Example: +/// +/// ```moonbit +/// test "Byte::to_int64" { +/// let b = b'\xFF' +/// inspect!(b.to_int64(), content="255") +/// } +/// ``` pub fn Byte::to_int64(self : Byte) -> Int64 { self.to_int().to_int64() } @@ -330,166 +2022,1230 @@ pub fn Byte::to_int64(self : Byte) -> Int64 { pub fn UInt::reinterpret_as_int(self : UInt) -> Int = "%u32.to_i32_reinterpret" ///| +/// Reinterprets an unsigned 32-bit integer as a signed 32-bit integer. For +/// values within the range of 0 to 2^31-1, the value remains the same. For +/// values within the range of 2^31 to 2^32-1, the value becomes negative due to +/// two's complement representation. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be reinterpreted. +/// +/// Returns a signed 32-bit integer that has the same bit pattern as the input +/// unsigned integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::to_int" { +/// let a = 42U +/// inspect!(a.reinterpret_as_int(), content="42") +/// let b = 4294967295U // maximum value of UInt (2^32 - 1) +/// inspect!(b.reinterpret_as_int(), content="-1") // becomes -1 when reinterpreted as Int +/// } +/// ``` +/// /// @alert deprecated "Use `reinterpret_as_int` instead" /// @coverage.skip pub fn UInt::to_int(self : UInt) -> Int = "%u32.to_i32_reinterpret" ///| +/// Performs addition between two unsigned 32-bit integers. If the result +/// overflows, it wraps around according to the rules of modular arithmetic +/// (2^32). +/// +/// Parameters: +/// +/// * `self` : The first unsigned 32-bit integer operand. +/// * `other` : The second unsigned 32-bit integer operand to be added. +/// +/// Returns the sum of the two unsigned integers, wrapped around if necessary. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_add" { +/// let a = 42U +/// let b = 100U +/// inspect!(a + b, content="142") +/// +/// // Demonstrate overflow behavior +/// let max = 4294967295U // UInt::max_value +/// inspect!(max + 1U, content="0") +/// } +/// ``` pub fn UInt::op_add(self : UInt, other : UInt) -> UInt = "%u32.add" ///| +/// Performs subtraction between two unsigned 32-bit integers. When the result +/// would be negative, the function wraps around using modular arithmetic (2^32). +/// +/// Parameters: +/// +/// * `self` : The first unsigned 32-bit integer (minuend). +/// * `other` : The second unsigned 32-bit integer to subtract from the first +/// (subtrahend). +/// +/// Returns a new unsigned 32-bit integer representing the difference between the +/// two numbers. If the result would be negative, it wraps around to a positive +/// number by adding 2^32 repeatedly until the result is in range. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_sub" { +/// let a = 5U +/// let b = 3U +/// inspect!(a - b, content="2") +/// let c = 3U +/// let d = 5U +/// inspect!(c - d, content="4294967294") // wraps around to 2^32 - 2 +/// } +/// ``` pub fn UInt::op_sub(self : UInt, other : UInt) -> UInt = "%u32.sub" ///| +/// Performs multiplication between two unsigned 32-bit integers. The result +/// wraps around if it exceeds the maximum value of `UInt`. +/// +/// Parameters: +/// +/// * `self` : The first unsigned integer operand. +/// * `other` : The second unsigned integer operand. +/// +/// Returns the product of the two unsigned integers. If the result exceeds the +/// maximum value of `UInt` (4294967295), it wraps around to the corresponding +/// value modulo 2^32. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_mul" { +/// let a = 3U +/// let b = 4U +/// inspect!(a * b, content="12") +/// let max = 4294967295U +/// inspect!(max * 2U, content="4294967294") // Wraps around to max * 2 % 2^32 +/// } +/// ``` pub fn UInt::op_mul(self : UInt, other : UInt) -> UInt = "%u32.mul" ///| +/// Performs division between two unsigned 32-bit integers. The operation follows +/// standard unsigned integer division rules, where the result is truncated +/// towards zero. +/// +/// Parameters: +/// +/// * `self` : The dividend (the number to be divided). +/// * `other` : The divisor (the number to divide by). +/// +/// Returns an unsigned 32-bit integer representing the quotient of the division. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_div" { +/// let a = 42U +/// let b = 5U +/// inspect!(a / b, content="8") // Using infix operator +/// } +/// +/// test "panic UInt::op_div/division_by_zero" { +/// let a = 42U +/// ignore(a / 0U) // Throws runtime error: division by zero +/// } +/// ``` pub fn UInt::op_div(self : UInt, other : UInt) -> UInt = "%u32.div" ///| +/// Calculates the remainder of dividing one unsigned integer by another. +/// +/// Parameters: +/// +/// * `self` : The unsigned integer dividend. +/// * `other` : The unsigned integer divisor. +/// +/// Returns the remainder of the division operation. +/// +/// Throws a panic if `other` is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_mod" { +/// let a = 17U +/// let b = 5U +/// inspect!(a % b, content="2") // 17 divided by 5 gives quotient 3 and remainder 2 +/// inspect!(7U % 4U, content="3") +/// } +/// +/// test "panic UInt::op_mod/division_by_zero" { +/// let a = 42U +/// ignore(a % 0U) // Panics: division by zero +/// } +/// ``` pub fn UInt::op_mod(self : UInt, other : UInt) -> UInt = "%u32.mod" ///| +/// Compares two unsigned 32-bit integers for equality. +/// +/// Parameters: +/// +/// * `self` : The first unsigned integer operand. +/// * `other` : The second unsigned integer operand to compare with. +/// +/// Returns `true` if both integers have the same value, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_equal" { +/// let a = 42U +/// let b = 42U +/// let c = 24U +/// inspect!(a == b, content="true") +/// inspect!(a == c, content="false") +/// } +/// ``` pub fn UInt::op_equal(self : UInt, other : UInt) -> Bool = "%u32.eq" ///| +/// Checks if two unsigned 32-bit integers are not equal. +/// +/// Parameters: +/// +/// * `self` : The first unsigned integer to compare. +/// * `other` : The second unsigned integer to compare. +/// +/// Returns `true` if the two integers are not equal, `false` otherwise. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_neq" { +/// let a = 42U +/// let b = 24U +/// inspect!(a != b, content="true") +/// inspect!(a != a, content="false") +/// } +/// ``` pub fn UInt::op_neq(self : UInt, other : UInt) -> Bool = "%u32.ne" ///| +/// Compares two unsigned 32-bit integers and returns their relative order. +/// +/// Parameters: +/// +/// * `self` : The first unsigned integer to compare. +/// * `other` : The second unsigned integer to compare against. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::compare" { +/// let a = 42U +/// let b = 24U +/// inspect!(a.compare(b), content="1") // 42 > 24 +/// inspect!(b.compare(a), content="-1") // 24 < 42 +/// inspect!(a.compare(a), content="0") // 42 = 42 +/// } +/// ``` pub fn UInt::compare(self : UInt, other : UInt) -> Int = "%u32.compare" ///| +/// Performs a bitwise AND operation between two unsigned 32-bit integers. For +/// each bit position, the result is 1 if the bits at that position in both +/// operands are 1, and 0 otherwise. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 32-bit integer operand. +/// * `other` : The second unsigned 32-bit integer operand. +/// +/// Returns an unsigned 32-bit integer representing the result of the bitwise AND +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::land" { +/// let a = 0xF0F0U // 1111_0000_1111_0000 +/// let b = 0xFF00U // 1111_1111_0000_0000 +/// inspect!(a & b, content="61440") // 1111_0000_0000_0000 = 61440 +/// } +/// ``` + pub fn UInt::land(self : UInt, other : UInt) -> UInt = "%u32.bitand" ///| +/// Performs a bitwise OR operation between two unsigned 32-bit integers. For +/// each bit position, the result is 1 if at least one of the corresponding bits +/// in either operand is 1. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 32-bit integer operand. +/// * `other` : The second unsigned 32-bit integer operand. +/// +/// Returns the result of the bitwise OR operation as an unsigned 32-bit integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::lor" { +/// let a = 0xF0F0U // Binary: 1111_0000_1111_0000 +/// let b = 0x0F0FU // Binary: 0000_1111_0000_1111 +/// inspect!(a | b, content="65535") // Binary: 1111_1111_1111_1111 +/// } +/// ``` + pub fn UInt::lor(self : UInt, other : UInt) -> UInt = "%u32.bitor" ///| +/// Performs a bitwise XOR (exclusive OR) operation between two unsigned 32-bit +/// integers. Each bit in the result is set to 1 if the corresponding bits in the +/// operands are different, and 0 if they are the same. +/// +/// Parameters: +/// +/// * `self` : The first unsigned 32-bit integer operand. +/// * `other` : The second unsigned 32-bit integer operand. +/// +/// Returns the result of the bitwise XOR operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::lxor" { +/// let a = 0xFF00U // Binary: 1111_1111_0000_0000 +/// let b = 0x0F0FU // Binary: 0000_1111_0000_1111 +/// inspect!(a ^ b, content="61455") // Binary: 1111_0000_0000_1111 +/// } +/// ``` pub fn UInt::lxor(self : UInt, other : UInt) -> UInt = "%u32.bitxor" ///| +/// Performs a bitwise NOT operation on an unsigned 32-bit integer. Flips all +/// bits in the number (changes each 0 to 1 and each 1 to 0). +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer value on which to perform the bitwise +/// NOT operation. +/// +/// Returns a new unsigned 32-bit integer where each bit is inverted from the +/// input value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::lnot" { +/// let x = 0xFF00U // Binary: 1111_1111_0000_0000 +/// inspect!(x.lnot(), content="4294902015") // Binary: ...0000_0000_1111_1111 +/// } +/// ``` pub fn UInt::lnot(self : UInt) -> UInt = "%u32.bitnot" ///| +/// Performs a left shift operation on an unsigned 32-bit integer. Shifts each +/// bit in the number to the left by the specified number of positions, filling +/// the rightmost positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be shifted. +/// * `shift` : The number of positions to shift the bits. Must be non-negative +/// and less than 32. Values outside this range are wrapped to fit within it +/// (i.e., `shift & 31`). +/// +/// Returns a new `UInt` value representing the result of shifting the bits left +/// by the specified number of positions. Each position shifted multiplies the +/// number by 2. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::lsl" { +/// let x = 1U +/// inspect!(x << 3, content="8") // Using the recommended operator +/// let y = 8U +/// inspect!(y << 1, content="16") // Using the recommended operator +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip pub fn UInt::lsl(self : UInt, shift : Int) -> UInt = "%u32.shl" ///| +/// Performs a left shift operation on an unsigned 32-bit integer. Shifts each +/// bit in the integer to the left by the specified number of positions, filling +/// the rightmost positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be shifted. +/// * `shift` : The number of positions to shift left. Must be between 0 and 31 +/// inclusive. Values outside this range will be masked with `& 31`. +/// +/// Returns a new `UInt` value containing the result of the left shift operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::shl" { +/// let x = 1U +/// inspect!(x << 3, content="8") // Binary: 1 -> 1000 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `<<` instead" /// @coverage.skip + pub fn UInt::shl(self : UInt, shift : Int) -> UInt = "%u32.shl" ///| +/// Performs a logical right shift on an unsigned 32-bit integer. Each bit in the +/// input value is shifted right by the specified number of positions, with zeros +/// shifted in from the left. DEPRECATED: Use the `>>` operator instead. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be shifted. +/// * `shift` : The number of positions to shift right. Must be non-negative. +/// +/// Returns a new `UInt` value representing the result of the logical right shift +/// operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::lsr" { +/// let x = 0xF0000000U +/// inspect!(x >> 4, content="251658240") // Using the recommended operator +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip pub fn UInt::lsr(self : UInt, shift : Int) -> UInt = "%u32.shr" ///| +/// Performs a logical right shift operation on an unsigned 32-bit integer by a +/// specified number of positions. All bits shifted in from the left are zeros. +/// +/// Parameters: +/// +/// * `number` : The unsigned 32-bit integer to be shifted. +/// * `shift` : The number of positions to shift right. Must be non-negative. +/// +/// Returns a new `UInt` value that represents the result of shifting all bits in +/// `number` to the right by `shift` positions. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::shr" { +/// let x = 0xFF000000U +/// inspect!(x >> 8, content="16711680") // 0x00FF0000 +/// } +/// ``` +/// /// @alert deprecated "Use infix operator `>>` instead" /// @coverage.skip + pub fn UInt::shr(self : UInt, shift : Int) -> UInt = "%u32.shr" ///| +/// Performs a left shift operation on an unsigned 32-bit integer. Each bit in +/// the integer is shifted left by the specified number of positions, and zeros +/// are filled in from the right. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be shifted. +/// * `shift` : The number of positions to shift. Only the least significant 5 +/// bits are used, effectively making the shift count always between 0 and 31. +/// +/// Returns a new unsigned 32-bit integer that is the result of shifting `self` +/// left by `shift` positions. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_shl" { +/// let x = 1U +/// inspect!(x << 3, content="8") // Binary: 1 -> 1000 +/// let y = 0xFFFFFFFFU +/// inspect!(y << 16, content="4294901760") // All bits after position 16 are discarded +/// } +/// ``` pub fn UInt::op_shl(self : UInt, shift : Int) -> UInt = "%u32.shl" ///| +/// Performs a logical right shift operation on an unsigned 32-bit integer. The +/// operation shifts all bits to the right by a specified number of positions, +/// filling the leftmost positions with zeros. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be shifted. +/// * `shift` : The number of positions to shift right. If this value is +/// negative, the behavior is undefined. Values larger than 31 are masked with `& +/// 31`. +/// +/// Returns a new unsigned 32-bit integer containing the result of the right +/// shift operation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::op_shr" { +/// let x = 0xFF000000U +/// inspect!(x >> 8, content="16711680") // 0x00FF0000 +/// inspect!(x >> 24, content="255") // 0x000000FF +/// } +/// +/// test "UInt::op_shr/large_shift" { +/// let x = 0xFF000000U +/// inspect!(x >> 32, content="4278190080") // Same as x >> 0 due to masking +/// } +/// ``` pub fn UInt::op_shr(self : UInt, shift : Int) -> UInt = "%u32.shr" ///| +/// Counts the number of leading zero bits in an unsigned 32-bit integer, +/// starting from the most significant bit. +/// +/// Parameters: +/// +/// * `value` : The unsigned 32-bit integer whose leading zeros are to be +/// counted. +/// +/// Returns the number of consecutive zeros starting from the most significant +/// bit. For a zero value, returns 32. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::clz" { +/// inspect!(0U.clz(), content="32") +/// inspect!(1U.clz(), content="31") +/// inspect!(0x80000000U.clz(), content="0") +/// } +/// ``` pub fn UInt::clz(self : UInt) -> Int = "%u32.clz" ///| +/// Counts the number of trailing zero bits in an unsigned 32-bit integer, +/// starting from the least significant bit. For a zero input, returns 32. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer whose trailing zeros are to be +/// counted. +/// +/// Returns the number of consecutive zeros at the least significant end of the +/// binary representation. Returns 32 if the input is zero. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::ctz" { +/// let x = 24U // Binary: ...011000 +/// inspect!(x.ctz(), content="3") // 3 trailing zeros +/// let y = 0U +/// inspect!(y.ctz(), content="32") // All bits are zero +/// } +/// ``` + pub fn UInt::ctz(self : UInt) -> Int = "%u32.ctz" ///| +/// Counts the number of 1 bits (population count) in the binary representation +/// of an unsigned 32-bit integer. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer whose bits are to be counted. +/// +/// Returns an integer representing the count of set bits (1s) in the binary +/// representation. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::popcnt" { +/// let x = 0xF0F0U // Binary: 1111 0000 1111 0000 +/// inspect!(x.popcnt(), content="8") // Has 8 bits set to 1 +/// } +/// ``` pub fn UInt::popcnt(self : UInt) -> Int = "%u32.popcnt" ///| +/// Converts an unsigned 32-bit integer to an unsigned 64-bit integer by +/// zero-extending it. The resulting value preserves the original number's +/// magnitude while using 64 bits to represent it. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer (`UInt`) to be converted. +/// +/// Returns an unsigned 64-bit integer (`UInt64`) representing the same numerical +/// value as the input. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::to_uint64" { +/// let n = 42U +/// inspect!(n.to_uint64(), content="42") +/// let max = 4294967295U // Maximum value of UInt +/// inspect!(max.to_uint64(), content="4294967295") +/// } +/// ``` pub fn UInt::to_uint64(self : UInt) -> UInt64 { UInt64::extend_uint(self) } ///| +/// Converts an unsigned 32-bit integer to a byte by taking its least significant +/// 8 bits. Any bits beyond the first 8 bits are truncated. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be converted. Only the least +/// significant 8 bits will be used. +/// +/// Returns a byte containing the least significant 8 bits of the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::to_byte" { +/// let n = 258U // In binary: 100000010 +/// inspect!(n.to_byte(), content="b'\\x02'") // Only keeps 00000010 +/// let big = 4294967295U // Maximum value of UInt +/// inspect!(big.to_byte(), content="b'\\xFF'") // Only keeps 11111111 +/// } +/// ``` pub fn UInt::to_byte(self : UInt) -> Byte { self.reinterpret_as_int().to_byte() } ///| -// Float primitive +/// Performs unary negation on a 32-bit floating-point number. Returns the +/// arithmetic inverse of the operand. +/// +/// Parameters: +/// +/// * `self` : The floating-point number to negate. +/// +/// Returns a new floating-point number with the same magnitude but opposite sign +/// as the input. Special cases: +/// +/// * Negating NaN returns NaN +/// * Negating +0.0 returns -0.0 +/// * Negating -0.0 returns +0.0 +/// * Negating +Infinity returns -Infinity +/// * Negating -Infinity returns +Infinity +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_neg" { +/// let f = 3.14.to_float() +/// inspect!((-f).to_double(), content="-3.140000104904175") +/// let zero = 0.0.to_float() +/// inspect!((-zero).to_double(), content="0") +/// } +/// ``` pub fn Float::op_neg(self : Float) -> Float = "%f32.neg" ///| +/// Performs addition between two single-precision floating-point numbers. +/// +/// Parameters: +/// +/// * `self` : The first floating-point operand. +/// * `other` : The second floating-point operand to be added to the first +/// operand. +/// +/// Returns a single-precision floating-point number representing the sum of the +/// two operands. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_add" { +/// let a = 3.14.to_float() +/// let b = 2.86.to_float() +/// let sum = a + b +/// inspect!(sum.to_double(), content="6") +/// } +/// ``` pub fn Float::op_add(self : Float, other : Float) -> Float = "%f32.add" ///| +/// Performs subtraction between two single-precision floating-point numbers. +/// +/// Parameters: +/// +/// * `self` : The first floating-point number (minuend). +/// * `other` : The second floating-point number (subtrahend). +/// +/// Returns a new floating-point number representing the difference between +/// `self` and `other`. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_sub" { +/// let x = 3.14.to_float() +/// let y = 1.0.to_float() +/// let result = x - y +/// inspect!(result.to_double(), content="2.140000104904175") +/// } +/// ``` pub fn Float::op_sub(self : Float, other : Float) -> Float = "%f32.sub" ///| +/// Performs multiplication between two single-precision floating-point numbers +/// according to IEEE 754 rules. +/// +/// Parameters: +/// +/// * `self` : The first floating-point number operand. +/// * `other` : The second floating-point number operand to multiply with the +/// first. +/// +/// Returns a single-precision floating-point number that is the product of the +/// two operands. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_mul" { +/// let x = Int::to_float(2) +/// let y = Int::to_float(3) +/// let z = x * y +/// inspect!(z.to_double(), content="6") +/// } +/// ``` pub fn Float::op_mul(self : Float, other : Float) -> Float = "%f32.mul" ///| +/// Performs division between two 32-bit floating-point numbers according to IEEE +/// 754 rules. +/// +/// Parameters: +/// +/// * `self` : The dividend floating-point number. +/// * `other` : The divisor floating-point number. +/// +/// Returns a new floating-point number representing the quotient of the +/// division. Special cases follow IEEE 754 rules: +/// +/// * Division by zero returns infinity (with the appropriate sign) +/// * Division of zero by zero returns NaN +/// * Division of infinity by infinity returns NaN +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_div" { +/// let a = 6.0.to_float() +/// let b = 2.0.to_float() +/// let result = (a / b).to_double() +/// inspect!(result, content="3") +/// inspect!((0.0.to_float() / 0.0.to_float()).to_double(), content="NaN") +/// } +/// ``` pub fn Float::op_div(self : Float, other : Float) -> Float = "%f32.div" ///| +/// Calculates the square root of a floating-point number. For non-negative +/// numbers, returns the principal square root. For negative numbers or NaN, +/// returns NaN. +/// +/// Parameters: +/// +/// * `self` : The floating-point number whose square root is to be calculated. +/// +/// Returns a 32-bit floating-point number representing the square root of the +/// input value: +/// +/// * For a positive number, returns its principal square root +/// * For zero (positive or negative), returns zero with the same sign +/// * For NaN or negative numbers, returns NaN +/// +/// Example: +/// +/// ```moonbit +/// test "Float::sqrt" { +/// let x = 16.0.to_float() +/// let root = x.sqrt() +/// inspect!(root.to_double(), content="4") +/// let neg = (-4.0).to_float() +/// let neg_root = neg.sqrt() +/// inspect!(neg_root.to_double(), content="NaN") +/// } +/// ``` pub fn Float::sqrt(self : Float) -> Float = "%f32.sqrt" ///| +/// Tests two floating-point numbers for equality. Follows IEEE 754 equality +/// comparison rules, where NaN values are not equal to any value, including +/// themselves. +/// +/// Parameters: +/// +/// * `self` : The first floating-point number to compare. +/// * `other` : The second floating-point number to compare. +/// +/// Returns `true` if both numbers are equal, `false` otherwise. Note that `-0.0` +/// and `+0.0` are considered equal. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_equal" { +/// let x = 3.14 +/// let y = 3.14 +/// let z = 0.0 / 0.0 // NaN +/// inspect!(x == y, content="true") +/// inspect!(z == z, content="false") // NaN is not equal to itself +/// } +/// ``` pub fn Float::op_equal(self : Float, other : Float) -> Bool = "%f32.eq" ///| +/// Tests if two single-precision floating-point numbers are not equal. This +/// operation follows IEEE 754 rules for floating-point comparison, including +/// special handling of NaN values. +/// +/// Parameters: +/// +/// * `self` : The first floating-point number to compare. +/// * `other` : The second floating-point number to compare. +/// +/// Returns `true` if the two floating-point numbers are not equal, `false` if +/// they are equal. Note that if either operand is NaN, the result is `true`. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::op_neq" { +/// let x = 1.0.to_float() +/// let y = 2.0.to_float() +/// let nan = (0.0 / 0.0).to_float() +/// inspect!(x != y, content="true") +/// inspect!(x != x, content="false") +/// inspect!(nan != nan, content="true") // NaN is not equal to itself +/// } +/// ``` pub fn Float::op_neq(self : Float, other : Float) -> Bool = "%f32.ne" ///| +/// Compares two 32-bit floating-point numbers and returns their relative order. +/// +/// Parameters: +/// +/// * `self` : The first floating-point number to compare. +/// * `other` : The second floating-point number to compare. +/// +/// Returns an integer indicating the relative order: +/// +/// * A negative value if `self` is less than `other` +/// * Zero if `self` equals `other` +/// * A positive value if `self` is greater than `other` +/// +/// Example: +/// +/// ```moonbit +/// test "Float::compare" { +/// let a = 3.14 +/// let b = 2.718 +/// inspect!(a.compare(b), content="1") // 3.14 > 2.718 +/// inspect!(b.compare(a), content="-1") // 2.718 < 3.14 +/// inspect!(a.compare(a), content="0") // 3.14 = 3.14 +/// } +/// ``` pub fn Float::compare(self : Float, other : Float) -> Int = "%f32.compare" ///| +/// Converts a 32-bit floating-point number to a double-precision (64-bit) +/// floating-point number. +/// +/// Parameters: +/// +/// * `self` : The 32-bit floating-point number to be converted. +/// +/// Returns a double-precision floating-point number that preserves the exact +/// value of the input. Since double-precision has more bits than +/// single-precision, this conversion is always exact and never loses precision. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::to_double" { +/// let f = 3.14.to_float() +/// inspect!(f.to_double(), content="3.140000104904175") +/// } +/// ``` pub fn Float::to_double(self : Float) -> Double = "%f32.to_f64" ///| +/// Reinterprets the bits of a 32-bit floating-point number as a 32-bit signed +/// integer without performing any numeric conversion. The bit pattern is +/// preserved exactly, only the type interpretation changes. +/// +/// Parameters: +/// +/// * `self` : The 32-bit floating-point number whose bits are to be +/// reinterpreted. +/// +/// Returns a 32-bit signed integer that has the same bit pattern as the input +/// floating-point number. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::reinterpret_as_int" { +/// let f = 1.0.to_float() +/// // IEEE 754 representation of 1.0 is 0x3F800000 +/// inspect!(f.reinterpret_as_int(), content="1065353216") +/// } +/// ``` pub fn Float::reinterpret_as_int(self : Float) -> Int = "%f32.to_i32_reinterpret" ///| +/// Reinterprets the bits of a 32-bit floating-point number as an unsigned 32-bit +/// integer without performing any numeric conversion. Preserves the exact bit +/// pattern of the input value, only changing how these bits are interpreted. +/// +/// Parameters: +/// +/// * `float` : The 32-bit floating-point number whose bits are to be +/// reinterpreted. +/// +/// Returns an unsigned 32-bit integer (`UInt`) that has the same bit pattern as +/// the input floating-point number. +/// +/// Example: +/// +/// ```moonbit +/// test "Float::reinterpret_as_uint" { +/// let x : Float = 1.0 +/// inspect!(x.reinterpret_as_uint(), content="1065353216") // Decimal representation of 0x3F800000 +/// } +/// ``` pub fn Float::reinterpret_as_uint(self : Float) -> UInt = "%f32.to_i32_reinterpret" ///| +/// Converts an integer to a 32-bit floating-point number. The conversion is +/// exact for small integers, but may lose precision for large integers due to +/// the limited precision of the floating-point format. +/// +/// Parameters: +/// +/// * `number` : The integer value to be converted to a floating-point number. +/// +/// Returns a 32-bit floating-point number representing the same value as the +/// input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_float" { +/// let n = 42 +/// let f = n.to_float() +/// // Convert back to double for comparison since Float doesn't implement Show +/// inspect!(f.to_double(), content="42") +/// } +/// ``` pub fn Int::to_float(self : Int) -> Float = "%i32.to_f32" ///| +/// Reinterprets the bits of a 32-bit integer as a single-precision +/// floating-point number according to IEEE 754 standard. The bit pattern of the +/// input is preserved, only the type interpretation changes. +/// +/// Parameters: +/// +/// * `self` : The 32-bit integer whose bits are to be reinterpreted as a +/// single-precision floating-point number. +/// +/// Returns a 32-bit floating-point number (`Float`) that has the same bit +/// pattern as the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::reinterpret_as_float" { +/// // 0x3F800000 represents 1.0 in IEEE 754 single-precision format +/// let n = 1065353216 // 0x3F800000 +/// inspect!(n.reinterpret_as_float().to_double(), content="1") +/// } +/// ``` pub fn Int::reinterpret_as_float(self : Int) -> Float = "%i32.to_f32_reinterpret" ///| +/// Reinterprets the bits of an unsigned 32-bit integer as a single-precision +/// floating-point number (IEEE 754). The bit pattern is preserved exactly, only +/// the type interpretation changes. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer whose bits are to be reinterpreted as +/// a single-precision floating-point number. +/// +/// Returns a single-precision floating-point number (`Float`) whose bit pattern +/// is identical to the input integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::reinterpret_as_float" { +/// let n = 0x3F800000U // Bit pattern for 1.0f +/// inspect!(n.reinterpret_as_float().to_double(), content="1") +/// } +/// ``` pub fn UInt::reinterpret_as_float(self : UInt) -> Float = "%i32.to_f32_reinterpret" ///| +/// Converts a byte value to a 32-bit floating-point number (IEEE 754 +/// single-precision format). The byte value is treated as an unsigned 8-bit +/// integer during the conversion. +/// +/// Parameters: +/// +/// * `byte` : The byte value to be converted to a float. +/// +/// Returns a 32-bit floating-point number representing the byte value. +/// +/// Example: +/// +/// ```moonbit +/// test "Byte::to_float" { +/// let b = b'\xFF' // 255 in decimal +/// let f = b.to_float() +/// // Convert to double for comparison since Float doesn't implement Show +/// inspect!(f.to_double(), content="255") +/// } +/// ``` pub fn Byte::to_float(self : Byte) -> Float = "%byte.to_f32" ///| +/// Converts a double-precision floating-point number to a single-precision +/// floating-point number. The conversion may result in a loss of precision due +/// to the reduced number of bits available in the single-precision format. +/// +/// Parameters: +/// +/// * `value` : The double-precision floating-point number to be converted. +/// +/// Returns a single-precision floating-point number that represents the closest +/// possible value to the input double-precision number. +/// +/// Example: +/// +/// ```moonbit +/// test "Double::to_float" { +/// let d = 3.14159265359 +/// inspect!(d.to_float().to_double(), content="3.1415927410125732") // Note the loss of precision +/// } +/// ``` pub fn Double::to_float(self : Double) -> Float = "%f64.to_f32" ///| +/// Converts an unsigned 32-bit integer to a single-precision floating-point +/// number. Due to the limited precision of the 32-bit floating-point format, +/// values above 16777216 (2^24) may lose precision during conversion. +/// +/// Parameters: +/// +/// * `self` : The unsigned 32-bit integer to be converted. +/// +/// Returns a 32-bit floating-point number that represents the same numerical +/// value as the input unsigned integer. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt::to_float" { +/// let n = 42U +/// inspect!(n.to_float().to_double(), content="42") +/// let big = 16777216U // 2^24 +/// inspect!(big.to_float().to_double(), content="16777216") // Last precisely representable integer +/// } +/// ``` pub fn UInt::to_float(self : UInt) -> Float = "%u32.to_f32" ///| +/// Converts a 16-bit signed integer to a 32-bit signed integer by sign +/// extension. +/// +/// Parameters: +/// +/// * `value` : The 16-bit signed integer to be converted. +/// +/// Returns a 32-bit signed integer that has the same value as the input. +/// +/// Example: +/// +/// ```moonbit +/// test "Int16::to_int" { +/// let n = Int::to_int16(42) +/// inspect!(n.to_int(), content="42") +/// let neg = Int::to_int16(-42) +/// inspect!(neg.to_int(), content="-42") +/// } +/// ``` pub fn Int16::to_int(self : Int16) -> Int = "%i16_to_i32" ///| +/// Converts a 16-bit signed integer to a byte by truncating its value to fit +/// within the byte range (0 to 255). Only the least significant 8 bits of the +/// integer are retained. +/// +/// Parameters: +/// +/// * `value` : The 16-bit signed integer to be converted to a byte. +/// +/// Returns a byte containing the least significant 8 bits of the input value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int16::to_byte" { +/// let x = Int::to_int16(258) // In binary: 0000_0001_0000_0010 +/// inspect!(x.to_byte(), content="b'\\x02'") // Only keeps 0000_0010 +/// } +/// ``` pub fn Int16::to_byte(self : Int16) -> Byte = "%i16_to_byte" ///| pub fn Int::to_int16(self : Int) -> Int16 = "%i32_to_i16" ///| +/// Converts a byte value to a 16-bit signed integer. The byte value is +/// sign-extended to 16 bits during the conversion. +/// +/// Parameters: +/// +/// * `byte` : The byte value to be converted to an `Int16`. +/// +/// Returns a 16-bit signed integer representing the same value as the input +/// byte. +/// +/// Example: +/// +/// ```moonbit +/// test "Byte::to_int16" { +/// let b = b'\xFF' // -1 as a signed byte +/// inspect!(b.to_int16(), content="255") // Sign is preserved +/// let p = b'\x7F' // 127 as a signed byte +/// inspect!(p.to_int16(), content="127") +/// } +/// ``` pub fn Byte::to_int16(self : Byte) -> Int16 = "%byte_to_i16" ///| +/// Converts an unsigned 16-bit integer to a 32-bit signed integer. The value is +/// zero-extended to fill the higher bits. +/// +/// Parameters: +/// +/// * `value` : The unsigned 16-bit integer to be converted. +/// +/// Returns a 32-bit signed integer. Since the input value is always non-negative +/// and less than 65536, the conversion never results in overflow. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt16::to_int" { +/// let x = Int::to_uint16(42) +/// inspect!(x.to_int(), content="42") +/// let max = Int::to_uint16(65535) // maximum value of UInt16 +/// inspect!(max.to_int(), content="65535") +/// } +/// ``` + pub fn UInt16::to_int(self : UInt16) -> Int = "%u16_to_i32" ///| +/// Converts a 16-bit unsigned integer to an 8-bit byte by truncating the higher +/// bits. +/// +/// Parameters: +/// +/// * `value` : The 16-bit unsigned integer to be converted. +/// +/// Returns a byte containing the least significant 8 bits of the input value. +/// +/// Example: +/// +/// ```moonbit +/// test "UInt16::to_byte" { +/// let x = Int::to_uint16(258) // Binary: 0000_0001_0000_0010 +/// inspect!(x.to_byte(), content="b'\\x02'") // Only keeps 0000_0010 +/// } +/// ``` pub fn UInt16::to_byte(self : UInt16) -> Byte = "%u16_to_byte" ///| +/// Converts a 32-bit signed integer to a 16-bit unsigned integer by truncating +/// its value to fit within the range of 0 to 65535. +/// +/// Parameters: +/// +/// * `integer` : The 32-bit signed integer to be converted. Values outside the +/// range of UInt16 will be truncated to fit. +/// +/// Returns a 16-bit unsigned integer containing the lower 16 bits of the input +/// value. +/// +/// Example: +/// +/// ```moonbit +/// test "Int::to_uint16" { +/// let n = 42 +/// inspect!(n.to_uint16(), content="42") +/// let neg = -1 +/// inspect!(neg.to_uint16(), content="65535") // -1 becomes max value of UInt16 +/// let large = 65536 +/// inspect!(large.to_uint16(), content="0") // Values wrap around +/// } +/// ``` pub fn Int::to_uint16(self : Int) -> UInt16 = "%i32_to_u16" ///| +/// Converts a byte value to a 16-bit unsigned integer by zero-extending it. +/// +/// Parameters: +/// +/// * `byte` : The byte value to be converted. +/// +/// Returns a 16-bit unsigned integer (`UInt16`) representing the same value as +/// the input byte. +/// +/// Example: +/// +/// ```moonbit +/// test "Byte::to_uint16" { +/// let b = b'\xFF' // byte with value 255 +/// inspect!(b.to_uint16(), content="255") +/// let zero = b'\x00' +/// inspect!(zero.to_uint16(), content="0") +/// } +/// ``` pub fn Byte::to_uint16(self : Byte) -> UInt16 = "%byte_to_u16"