diff --git a/doc/library/sparse/index.rst b/doc/library/sparse/index.rst index ff8a87aeff..98d58c6758 100644 --- a/doc/library/sparse/index.rst +++ b/doc/library/sparse/index.rst @@ -196,7 +196,7 @@ List of Implemented Operations - ``ceil`` - ``floor`` - ``trunc`` - - ``sgn`` + - ``sign`` - ``log1p`` - ``expm1`` - ``sqr`` diff --git a/doc/library/tensor/basic.rst b/doc/library/tensor/basic.rst index a386de0032..fab197dd75 100644 --- a/doc/library/tensor/basic.rst +++ b/doc/library/tensor/basic.rst @@ -1462,7 +1462,7 @@ Mathematical Returns a variable representing the base e, 2 or 10 logarithm of a. -.. function:: sgn(a) +.. function:: sign(a) Returns a variable representing the sign of a. diff --git a/pytensor/compile/profiling.py b/pytensor/compile/profiling.py index b3befce77f..1af2147acd 100644 --- a/pytensor/compile/profiling.py +++ b/pytensor/compile/profiling.py @@ -1509,7 +1509,7 @@ def print_tips(self, file): aes.Second, aes.Identity, aes.Cast, - aes.Sgn, + aes.Sign, aes.Neg, aes.Reciprocal, aes.Sqr, diff --git a/pytensor/scalar/basic.py b/pytensor/scalar/basic.py index b74d305edc..36f1527c66 100644 --- a/pytensor/scalar/basic.py +++ b/pytensor/scalar/basic.py @@ -2566,7 +2566,7 @@ def L_op(self, inputs, outputs, gout): return [x.zeros_like()] if x.type in float_types: - return (gz * sgn(x),) + return (gz * sign(x),) return (gz * x / _abs(x),) # formula works for complex and real def c_code(self, node, name, inputs, outputs, sub): @@ -2590,7 +2590,7 @@ def c_code(self, node, name, inputs, outputs, sub): abs = Abs(same_out) -class Sgn(UnaryScalarOp): +class Sign(UnaryScalarOp): nfunc_spec = ("sign", 1, 1) @staticmethod @@ -2625,7 +2625,7 @@ def c_code(self, node, name, inputs, outputs, sub): ) if type in int_types: return f"{z} = ({x} >= 0) ? ({x} == 0) ? 0 : 1 : -1;" - raise ComplexError("complex has no sgn") + raise ComplexError("complex has no sign") def c_code_cache_version(self): s = super().c_code_cache_version() @@ -2635,7 +2635,7 @@ def c_code_cache_version(self): return s -sgn = Sgn(name="sgn") +sign = Sign(name="sign") class Ceil(UnaryScalarOp): diff --git a/pytensor/sparse/basic.py b/pytensor/sparse/basic.py index 6e0d98fd15..91c2e889e5 100644 --- a/pytensor/sparse/basic.py +++ b/pytensor/sparse/basic.py @@ -36,8 +36,8 @@ from pytensor.tensor.math import ( rad2deg, round_half_to_even, - sgn, sigmoid, + sign, sin, sinh, sqr, @@ -3184,8 +3184,8 @@ def rint(x): rint.__name__ = "rint" -@structured_monoid(sgn) # type: ignore[no-redef] -def sgn(x): +@structured_monoid(sign) # type: ignore[no-redef] +def sign(x): """ Elemwise signe of `x`. diff --git a/pytensor/tensor/inplace.py b/pytensor/tensor/inplace.py index 4f6cf638fb..afb7f7ac7c 100644 --- a/pytensor/tensor/inplace.py +++ b/pytensor/tensor/inplace.py @@ -104,7 +104,7 @@ def log10_inplace(a): @scalar_elemwise -def sgn_inplace(a): +def sign_inplace(a): """sign of `a` (inplace on `a`)""" diff --git a/pytensor/tensor/math.py b/pytensor/tensor/math.py index 86846c3249..66373400d9 100644 --- a/pytensor/tensor/math.py +++ b/pytensor/tensor/math.py @@ -982,7 +982,7 @@ def isclose(a, b, rtol=1.0e-5, atol=1.0e-8, equal_nan=False): # deal with signed inf values. this will make an array inf_eq of 0's # except where inf values have the same sign. both_infs = bitwise_and(a_inf, b_inf) - inf_signs_eq = eq(a_inf * sgn(a), b_inf * sgn(b)) + inf_signs_eq = eq(a_inf * sign(a), b_inf * sign(b)) inf_eq = bitwise_and(both_infs, inf_signs_eq) # now create the potential result combining close and inf_eq @@ -1092,9 +1092,19 @@ def log1p(a): @scalar_elemwise +def sign(a): + """sign of a""" + + def sgn(a): """sign of a""" + warnings.warn( + "sgn is deprecated and will stop working in the future, use sign instead.", + FutureWarning, + ) + return sign(a) + @scalar_elemwise def ceil(a): @@ -3038,6 +3048,7 @@ def matmul(x1: "ArrayLike", x2: "ArrayLike", dtype: Optional["DTypeLike"] = None "log10", "log1p", "sgn", + "sign", "ceil", "floor", "trunc", diff --git a/pytensor/tensor/rewriting/math.py b/pytensor/tensor/rewriting/math.py index cc5ada7459..ac42197199 100644 --- a/pytensor/tensor/rewriting/math.py +++ b/pytensor/tensor/rewriting/math.py @@ -72,8 +72,8 @@ from pytensor.tensor.math import ( prod, reciprocal, - sgn, sigmoid, + sign, softplus, sqr, sqrt, @@ -2289,7 +2289,7 @@ def check_for_x_over_absX(numerators, denominators): else: denominators.remove(den) numerators.remove(den.owner.inputs[0]) - numerators.append(sgn(den.owner.inputs[0])) + numerators.append(sign(den.owner.inputs[0])) return numerators, denominators diff --git a/pytensor/tensor/subtensor.py b/pytensor/tensor/subtensor.py index 7087cfd79a..12d7d0a3f8 100644 --- a/pytensor/tensor/subtensor.py +++ b/pytensor/tensor/subtensor.py @@ -199,7 +199,7 @@ def get_canonical_form_slice( if the resulting set of numbers needs to be reversed or not. """ - from pytensor.tensor import ge, lt, sgn, switch + from pytensor.tensor import ge, lt, sign, switch if not isinstance(theslice, slice): try: @@ -317,7 +317,7 @@ def switch_neg_step(a, b): return switch(is_step_neg, a, b) abs_step = abs(step) - sgn_step = sgn(step) + sgn_step = sign(step) defstart = switch_neg_step(length - 1, 0) defstop = switch_neg_step(-1, length) diff --git a/tests/sparse/test_basic.py b/tests/sparse/test_basic.py index b429962deb..c83e0eea19 100644 --- a/tests/sparse/test_basic.py +++ b/tests/sparse/test_basic.py @@ -3111,7 +3111,7 @@ def structured_function(*args): ) SgnTester = elemwise_checker( - sparse.sgn, + sparse.sign, np.sign, grad_test=False, test_dtypes=[ diff --git a/tests/tensor/rewriting/test_math.py b/tests/tensor/rewriting/test_math.py index dce979afc1..33dc17cbcb 100644 --- a/tests/tensor/rewriting/test_math.py +++ b/tests/tensor/rewriting/test_math.py @@ -74,8 +74,8 @@ prod, rad2deg, reciprocal, - sgn, sigmoid, + sign, sinh, softplus, sqr, @@ -877,7 +877,7 @@ def test_abs_mul_div(self): assert np.isfinite(f(0)) assert len(f.maker.fgraph.toposort()) == 2 - assert f.maker.fgraph.toposort()[0].op == sgn + assert f.maker.fgraph.toposort()[0].op == sign f = function([x], [(4 * x) / abs(x / 2)], mode=mode) f(0.1) @@ -886,7 +886,7 @@ def test_abs_mul_div(self): assert np.isfinite(f(0)) assert len(f.maker.fgraph.toposort()) == 2 - assert f.maker.fgraph.toposort()[0].op == sgn + assert f.maker.fgraph.toposort()[0].op == sign @pytest.mark.skip( reason="Current implementation of AlgebraicCanonizer does not " diff --git a/tests/tensor/test_inplace.py b/tests/tensor/test_inplace.py index 47aaafaf2f..dc5a432eca 100644 --- a/tests/tensor/test_inplace.py +++ b/tests/tensor/test_inplace.py @@ -38,7 +38,7 @@ reciprocal_inplace, round_half_away_from_zero_inplace, round_half_to_even_inplace, - sgn_inplace, + sign_inplace, sin_inplace, sinh_inplace, sqr_inplace, @@ -177,7 +177,7 @@ ) TestSgnInplaceBroadcast = makeBroadcastTester( - op=sgn_inplace, + op=sign_inplace, expected=np.sign, good=_good_broadcast_unary_normal_no_complex, inplace=True, diff --git a/tests/tensor/test_math.py b/tests/tensor/test_math.py index a80896da58..60ff3178b5 100644 --- a/tests/tensor/test_math.py +++ b/tests/tensor/test_math.py @@ -99,8 +99,8 @@ reciprocal, round_half_away_from_zero, round_half_to_even, - sgn, sigmoid, + sign, sin, sinh, smallest, @@ -386,7 +386,7 @@ def test_maximum_minimum_grad(): ) TestSgnBroadcast = makeBroadcastTester( - op=sgn, + op=sign, expected=np.sign, good=_good_broadcast_unary_normal_no_complex, grad=_grad_broadcast_unary_normal,