diff options
| author | antlilja <liljaanton2001@gmail.com> | 2023-07-17 00:21:45 +0200 |
|---|---|---|
| committer | Andrew Kelley <andrew@ziglang.org> | 2023-09-27 11:24:28 -0700 |
| commit | bcf4a1391331e52e4a06528530316970ded75c74 (patch) | |
| tree | 484d6472f552780d6482b8457e56b29f9a06379d /lib/std/math.zig | |
| parent | 1c02e58fc06aa3e429f963e600e126611df3626e (diff) | |
| download | zig-bcf4a1391331e52e4a06528530316970ded75c74.tar.gz zig-bcf4a1391331e52e4a06528530316970ded75c74.zip | |
Remove `@fabs`, fabs and absCast/Int from std lib
Replaces occurences of @fabs absCast and absInt with new @abs builtin.
Also removes the std.math.fabs alias from math.zig.
Diffstat (limited to 'lib/std/math.zig')
| -rw-r--r-- | lib/std/math.zig | 98 |
1 files changed, 4 insertions, 94 deletions
diff --git a/lib/std/math.zig b/lib/std/math.zig index 7e835059a3..f5ee7019cd 100644 --- a/lib/std/math.zig +++ b/lib/std/math.zig @@ -130,7 +130,7 @@ pub fn approxEqAbs(comptime T: type, x: T, y: T, tolerance: T) bool { if (isNan(x) or isNan(y)) return false; - return @fabs(x - y) <= tolerance; + return @abs(x - y) <= tolerance; } /// Performs an approximate comparison of two floating point values `x` and `y`. @@ -158,7 +158,7 @@ pub fn approxEqRel(comptime T: type, x: T, y: T, tolerance: T) bool { if (isNan(x) or isNan(y)) return false; - return @fabs(x - y) <= @max(@fabs(x), @fabs(y)) * tolerance; + return @abs(x - y) <= @max(@abs(x), @abs(y)) * tolerance; } test "approxEqAbs and approxEqRel" { @@ -466,7 +466,7 @@ pub fn shlExact(comptime T: type, a: T, shift_amt: Log2Int(T)) !T { /// Shifts left. Overflowed bits are truncated. /// A negative shift amount results in a right shift. pub fn shl(comptime T: type, a: T, shift_amt: anytype) T { - const abs_shift_amt = absCast(shift_amt); + const abs_shift_amt = @abs(shift_amt); const casted_shift_amt = blk: { if (@typeInfo(T) == .Vector) { @@ -510,7 +510,7 @@ test "shl" { /// Shifts right. Overflowed bits are truncated. /// A negative shift amount results in a left shift. pub fn shr(comptime T: type, a: T, shift_amt: anytype) T { - const abs_shift_amt = absCast(shift_amt); + const abs_shift_amt = @abs(shift_amt); const casted_shift_amt = blk: { if (@typeInfo(T) == .Vector) { @@ -740,52 +740,6 @@ fn testOverflow() !void { try testing.expect((shlExact(i32, 0b11, 4) catch unreachable) == 0b110000); } -/// Returns the absolute value of x, where x is a value of a signed integer type. -/// Does not convert and returns a value of a signed integer type. -/// Use `absCast` if you want to convert the result and get an unsigned type. -/// Use `@fabs` if you need the absolute value of a floating point value. -pub fn absInt(x: anytype) !@TypeOf(x) { - const T = @TypeOf(x); - return switch (@typeInfo(T)) { - .Int => |info| { - comptime assert(info.signedness == .signed); // must pass a signed integer to absInt - if (x == minInt(T)) { - return error.Overflow; - } else { - @setRuntimeSafety(false); - return if (x < 0) -x else x; - } - }, - .Vector => |vinfo| blk: { - switch (@typeInfo(vinfo.child)) { - .Int => |info| { - comptime assert(info.signedness == .signed); // must pass a signed integer to absInt - if (@reduce(.Or, x == @as(T, @splat(minInt(vinfo.child))))) { - return error.Overflow; - } - const zero: T = @splat(0); - break :blk @select(vinfo.child, x > zero, x, -x); - }, - else => @compileError("Expected vector of ints, found " ++ @typeName(T)), - } - }, - else => @compileError("Expected an int or vector, found " ++ @typeName(T)), - }; -} - -test "absInt" { - try testAbsInt(); - try comptime testAbsInt(); -} -fn testAbsInt() !void { - try testing.expect((absInt(@as(i32, -10)) catch unreachable) == 10); - try testing.expect((absInt(@as(i32, 10)) catch unreachable) == 10); - try testing.expectEqual(@Vector(3, i32){ 10, 10, 0 }, (absInt(@Vector(3, i32){ -10, 10, 0 }) catch unreachable)); - - try testing.expectError(error.Overflow, absInt(@as(i32, minInt(i32)))); - try testing.expectError(error.Overflow, absInt(@Vector(3, i32){ 10, -10, minInt(i32) })); -} - /// Divide numerator by denominator, rounding toward zero. Returns an /// error on overflow or when denominator is zero. pub fn divTrunc(comptime T: type, numerator: T, denominator: T) !T { @@ -968,50 +922,6 @@ fn testRem() !void { try testing.expectError(error.DivisionByZero, rem(f32, 10, 0)); } -/// Returns the absolute value of a floating point number. -/// Uses a dedicated hardware instruction when available. -/// This is the same as calling the builtin @fabs -pub inline fn fabs(value: anytype) @TypeOf(value) { - return @fabs(value); -} - -/// Returns the absolute value of the integer parameter. -/// Converts result type to unsigned if needed and returns a value of an unsigned integer type. -/// Use `absInt` if you want to keep your integer type signed. -pub fn absCast(x: anytype) switch (@typeInfo(@TypeOf(x))) { - .ComptimeInt => comptime_int, - .Int => |int_info| std.meta.Int(.unsigned, int_info.bits), - else => @compileError("absCast only accepts integers"), -} { - switch (@typeInfo(@TypeOf(x))) { - .ComptimeInt => { - if (x < 0) { - return -x; - } else { - return x; - } - }, - .Int => |int_info| { - if (int_info.signedness == .unsigned) return x; - const Uint = std.meta.Int(.unsigned, int_info.bits); - if (x < 0) { - return ~@as(Uint, @bitCast(x +% -1)); - } else { - return @as(Uint, @intCast(x)); - } - }, - else => unreachable, - } -} - -test "absCast" { - try testing.expectEqual(@as(u1, 1), absCast(@as(i1, -1))); - try testing.expectEqual(@as(u32, 999), absCast(@as(i32, -999))); - try testing.expectEqual(@as(u32, 999), absCast(@as(i32, 999))); - try testing.expectEqual(@as(u32, -minInt(i32)), absCast(@as(i32, minInt(i32)))); - try testing.expectEqual(999, absCast(-999)); -} - /// Returns the negation of the integer parameter. /// Result is a signed integer. pub fn negateCast(x: anytype) !std.meta.Int(.signed, @bitSizeOf(@TypeOf(x))) { |
