mirror of
https://github.com/dlang/phobos.git
synced 2025-05-04 00:54:05 +03:00
Again use core.math intrinsics instead of std.math wrappers
As in PR #7821 & PR #7825. Mostly changes imports from std.math being divided into submodules.
This commit is contained in:
parent
974a88a967
commit
efced87ae8
7 changed files with 43 additions and 42 deletions
|
@ -1105,9 +1105,9 @@ Complex!T atan(T)(Complex!T z) @safe pure nothrow @nogc
|
||||||
*/
|
*/
|
||||||
Complex!T sinh(T)(Complex!T z) @safe pure nothrow @nogc
|
Complex!T sinh(T)(Complex!T z) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
static import std.math;
|
static import core.math, std.math;
|
||||||
return Complex!T(std.math.sinh(z.re) * std.math.cos(z.im),
|
return Complex!T(std.math.sinh(z.re) * core.math.cos(z.im),
|
||||||
std.math.cosh(z.re) * std.math.sin(z.im));
|
std.math.cosh(z.re) * core.math.sin(z.im));
|
||||||
}
|
}
|
||||||
|
|
||||||
///
|
///
|
||||||
|
@ -1122,9 +1122,9 @@ Complex!T sinh(T)(Complex!T z) @safe pure nothrow @nogc
|
||||||
/// ditto
|
/// ditto
|
||||||
Complex!T cosh(T)(Complex!T z) @safe pure nothrow @nogc
|
Complex!T cosh(T)(Complex!T z) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
static import std.math;
|
static import core.math, std.math;
|
||||||
return Complex!T(std.math.cosh(z.re) * std.math.cos(z.im),
|
return Complex!T(std.math.cosh(z.re) * core.math.cos(z.im),
|
||||||
std.math.sinh(z.re) * std.math.sin(z.im));
|
std.math.sinh(z.re) * core.math.sin(z.im));
|
||||||
}
|
}
|
||||||
|
|
||||||
///
|
///
|
||||||
|
|
|
@ -24,7 +24,7 @@
|
||||||
*/
|
*/
|
||||||
module std.internal.math.errorfunction;
|
module std.internal.math.errorfunction;
|
||||||
import std.math;
|
import std.math;
|
||||||
import core.math : sqrt;
|
import core.math : fabs, sqrt;
|
||||||
|
|
||||||
pure:
|
pure:
|
||||||
nothrow:
|
nothrow:
|
||||||
|
@ -836,7 +836,7 @@ real erf(real x)
|
||||||
return -1.0;
|
return -1.0;
|
||||||
if (x == real.infinity)
|
if (x == real.infinity)
|
||||||
return 1.0;
|
return 1.0;
|
||||||
immutable ax = abs(x);
|
immutable ax = fabs(x);
|
||||||
if (ax > 1.0L)
|
if (ax > 1.0L)
|
||||||
return 1.0L - erfc(x);
|
return 1.0L - erfc(x);
|
||||||
|
|
||||||
|
@ -932,7 +932,7 @@ real expx2(real x, int sign)
|
||||||
const real M = 32_768.0;
|
const real M = 32_768.0;
|
||||||
const real MINV = 3.0517578125e-5L;
|
const real MINV = 3.0517578125e-5L;
|
||||||
|
|
||||||
x = abs(x);
|
x = fabs(x);
|
||||||
if (sign < 0)
|
if (sign < 0)
|
||||||
x = -x;
|
x = -x;
|
||||||
|
|
||||||
|
@ -985,7 +985,7 @@ Journal of Statistical Software <b>11</b>, (July 2004).
|
||||||
real normalDistributionImpl(real a)
|
real normalDistributionImpl(real a)
|
||||||
{
|
{
|
||||||
real x = a * SQRT1_2;
|
real x = a * SQRT1_2;
|
||||||
real z = abs(x);
|
real z = fabs(x);
|
||||||
|
|
||||||
if ( z < 1.0 )
|
if ( z < 1.0 )
|
||||||
return 0.5L + 0.5L * erf(x);
|
return 0.5L + 0.5L * erf(x);
|
||||||
|
|
|
@ -302,6 +302,7 @@ real hypot(real x, real y) @safe pure nothrow @nogc
|
||||||
// If one is huge and the other tiny, return the larger.
|
// If one is huge and the other tiny, return the larger.
|
||||||
// If both are huge, avoid overflow by scaling by 1/sqrt(real.max/2).
|
// If both are huge, avoid overflow by scaling by 1/sqrt(real.max/2).
|
||||||
// If both are tiny, avoid underflow by scaling by sqrt(real.min_normal*real.epsilon).
|
// If both are tiny, avoid underflow by scaling by sqrt(real.min_normal*real.epsilon).
|
||||||
|
import core.math : fabs, sqrt;
|
||||||
|
|
||||||
enum real SQRTMIN = 0.5 * sqrt(real.min_normal); // This is a power of 2.
|
enum real SQRTMIN = 0.5 * sqrt(real.min_normal); // This is a power of 2.
|
||||||
enum real SQRTMAX = 1.0L / SQRTMIN; // 2^^((max_exp)/2) = nextUp(sqrt(real.max))
|
enum real SQRTMAX = 1.0L / SQRTMIN; // 2^^((max_exp)/2) = nextUp(sqrt(real.max))
|
||||||
|
@ -418,6 +419,7 @@ real hypot(real x, real y) @safe pure nothrow @nogc
|
||||||
T hypot(T)(const T x, const T y, const T z) @safe pure nothrow @nogc
|
T hypot(T)(const T x, const T y, const T z) @safe pure nothrow @nogc
|
||||||
if (isFloatingPoint!T)
|
if (isFloatingPoint!T)
|
||||||
{
|
{
|
||||||
|
import core.math : fabs, sqrt;
|
||||||
import std.math.operations : fmax;
|
import std.math.operations : fmax;
|
||||||
const absx = fabs(x);
|
const absx = fabs(x);
|
||||||
const absy = fabs(y);
|
const absy = fabs(y);
|
||||||
|
@ -1010,7 +1012,7 @@ private T powIntegralImpl(PowType type, T)(T val)
|
||||||
private T powFloatingPointImpl(PowType type, T)(T x)
|
private T powFloatingPointImpl(PowType type, T)(T x)
|
||||||
{
|
{
|
||||||
import std.math.traits : copysign, isFinite;
|
import std.math.traits : copysign, isFinite;
|
||||||
import std.math.exponential : frexp, ldexp;
|
import std.math.exponential : frexp;
|
||||||
|
|
||||||
if (!x.isFinite)
|
if (!x.isFinite)
|
||||||
return x;
|
return x;
|
||||||
|
@ -1022,9 +1024,9 @@ private T powFloatingPointImpl(PowType type, T)(T x)
|
||||||
auto y = frexp(x, exp);
|
auto y = frexp(x, exp);
|
||||||
|
|
||||||
static if (type == PowType.ceil)
|
static if (type == PowType.ceil)
|
||||||
y = ldexp(cast(T) 0.5, exp + 1);
|
y = core.math.ldexp(cast(T) 0.5, exp + 1);
|
||||||
else
|
else
|
||||||
y = ldexp(cast(T) 0.5, exp);
|
y = core.math.ldexp(cast(T) 0.5, exp);
|
||||||
|
|
||||||
if (!y.isFinite)
|
if (!y.isFinite)
|
||||||
return cast(T) 0.0;
|
return cast(T) 0.0;
|
||||||
|
|
|
@ -64,7 +64,7 @@ version (D_HardFloat)
|
||||||
Unqual!F pow(F, G)(F x, G n) @nogc @trusted pure nothrow
|
Unqual!F pow(F, G)(F x, G n) @nogc @trusted pure nothrow
|
||||||
if (isFloatingPoint!(F) && isIntegral!(G))
|
if (isFloatingPoint!(F) && isIntegral!(G))
|
||||||
{
|
{
|
||||||
import std.math.algebraic : abs;
|
import core.math : fabs;
|
||||||
import std.math.rounding : floor;
|
import std.math.rounding : floor;
|
||||||
import std.math.traits : isNaN;
|
import std.math.traits : isNaN;
|
||||||
import std.traits : Unsigned;
|
import std.traits : Unsigned;
|
||||||
|
@ -100,13 +100,13 @@ if (isFloatingPoint!(F) && isIntegral!(G))
|
||||||
//
|
//
|
||||||
// We use the following two conclusions:
|
// We use the following two conclusions:
|
||||||
//
|
//
|
||||||
// m * floor(log2(abs(v))) >= F.max_exp
|
// m * floor(log2(fabs(v))) >= F.max_exp
|
||||||
// => abs(v) ^^ m > F.max == nextDown(F.infinity)
|
// => fabs(v) ^^ m > F.max == nextDown(F.infinity)
|
||||||
//
|
//
|
||||||
// m * (bias - ex - 1) >= bias + F.mant_dig - 1
|
// m * (bias - ex - 1) >= bias + F.mant_dig - 1
|
||||||
// => abs(v) ^^ m < 2 ^^ (-bias - F.mant_dig + 2) == nextUp(0.0)
|
// => fabs(v) ^^ m < 2 ^^ (-bias - F.mant_dig + 2) == nextUp(0.0)
|
||||||
//
|
//
|
||||||
// floor(log2(abs(v))) == ex - bias can be directly taken from the
|
// floor(log2(fabs(v))) == ex - bias can be directly taken from the
|
||||||
// exponent of the floating point represantation, to avoid long
|
// exponent of the floating point represantation, to avoid long
|
||||||
// calculations here.
|
// calculations here.
|
||||||
|
|
||||||
|
@ -132,8 +132,8 @@ if (isFloatingPoint!(F) && isIntegral!(G))
|
||||||
// in CTFE we cannot access the bit patterns and have therefore to
|
// in CTFE we cannot access the bit patterns and have therefore to
|
||||||
// fall back to the (slower) general case
|
// fall back to the (slower) general case
|
||||||
// skipping subnormals by setting ex = bias
|
// skipping subnormals by setting ex = bias
|
||||||
ex = abs(v) == F.infinity ? 2 * bias + 1 :
|
ex = fabs(v) == F.infinity ? 2 * bias + 1 :
|
||||||
(abs(v) < F.min_normal ? bias : cast(ulong) (floor(log2(abs(v))) + bias));
|
(fabs(v) < F.min_normal ? bias : cast(ulong) (floor(log2(fabs(v))) + bias));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -148,8 +148,8 @@ if (isFloatingPoint!(F) && isIntegral!(G))
|
||||||
// In the general case we have to fall back to log2, which is slower, but still
|
// In the general case we have to fall back to log2, which is slower, but still
|
||||||
// a certain speed gain compared to not bailing out early.
|
// a certain speed gain compared to not bailing out early.
|
||||||
// skipping subnormals by setting ex = bias
|
// skipping subnormals by setting ex = bias
|
||||||
ulong ex = abs(v) == F.infinity ? 2 * bias + 1 :
|
ulong ex = fabs(v) == F.infinity ? 2 * bias + 1 :
|
||||||
(abs(v) < F.min_normal ? bias : cast(ulong) (floor(log2(abs(v))) + bias));
|
(fabs(v) < F.min_normal ? bias : cast(ulong) (floor(log2(fabs(v))) + bias));
|
||||||
}
|
}
|
||||||
|
|
||||||
// m * (...) can exceed ulong.max, we therefore first check m >= (...).
|
// m * (...) can exceed ulong.max, we therefore first check m >= (...).
|
||||||
|
@ -490,7 +490,7 @@ if (isIntegral!I && isFloatingPoint!F)
|
||||||
Unqual!(Largest!(F, G)) pow(F, G)(F x, G y) @nogc @trusted pure nothrow
|
Unqual!(Largest!(F, G)) pow(F, G)(F x, G y) @nogc @trusted pure nothrow
|
||||||
if (isFloatingPoint!(F) && isFloatingPoint!(G))
|
if (isFloatingPoint!(F) && isFloatingPoint!(G))
|
||||||
{
|
{
|
||||||
import std.math.algebraic : fabs, sqrt;
|
import core.math : fabs, sqrt;
|
||||||
import std.math.traits : isInfinity, isNaN, signbit;
|
import std.math.traits : isInfinity, isNaN, signbit;
|
||||||
|
|
||||||
alias Float = typeof(return);
|
alias Float = typeof(return);
|
||||||
|
@ -1203,7 +1203,7 @@ private T expImpl(T)(T x) @safe pure nothrow @nogc
|
||||||
}
|
}
|
||||||
|
|
||||||
// Scale by power of 2.
|
// Scale by power of 2.
|
||||||
x = ldexp(x, n);
|
x = core.math.ldexp(x, n);
|
||||||
|
|
||||||
return x;
|
return x;
|
||||||
}
|
}
|
||||||
|
@ -1697,7 +1697,7 @@ private T expm1Impl(T)(T x) @safe pure nothrow @nogc
|
||||||
|
|
||||||
// We have qx = exp(remainder LN2) - 1, so:
|
// We have qx = exp(remainder LN2) - 1, so:
|
||||||
// exp(x) - 1 = 2^^n (qx + 1) - 1 = 2^^n qx + 2^^n - 1.
|
// exp(x) - 1 = 2^^n (qx + 1) - 1 = 2^^n qx + 2^^n - 1.
|
||||||
px = ldexp(cast(T) 1.0, n);
|
px = core.math.ldexp(cast(T) 1.0, n);
|
||||||
x = px * qx + (px - cast(T) 1.0);
|
x = px * qx + (px - cast(T) 1.0);
|
||||||
|
|
||||||
return x;
|
return x;
|
||||||
|
@ -2091,7 +2091,7 @@ private T exp2Impl(T)(T x) @nogc @safe pure nothrow
|
||||||
}
|
}
|
||||||
|
|
||||||
// Scale by power of 2.
|
// Scale by power of 2.
|
||||||
x = ldexp(x, n);
|
x = core.math.ldexp(x, n);
|
||||||
|
|
||||||
return x;
|
return x;
|
||||||
}
|
}
|
||||||
|
@ -3145,7 +3145,7 @@ real log(real x) @safe pure nothrow @nogc
|
||||||
real log10(real x) @safe pure nothrow @nogc
|
real log10(real x) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
import std.math.constants : LOG2, LN2, SQRT1_2;
|
import std.math.constants : LOG2, LN2, SQRT1_2;
|
||||||
import std.math.algebraic : fabs, poly;
|
import std.math.algebraic : poly;
|
||||||
import std.math.traits : isNaN, isInfinity, signbit;
|
import std.math.traits : isNaN, isInfinity, signbit;
|
||||||
|
|
||||||
version (INLINE_YL2X)
|
version (INLINE_YL2X)
|
||||||
|
@ -3251,7 +3251,6 @@ real log10(real x) @safe pure nothrow @nogc
|
||||||
*/
|
*/
|
||||||
real log1p(real x) @safe pure nothrow @nogc
|
real log1p(real x) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
import std.math.algebraic : fabs;
|
|
||||||
import std.math.traits : isNaN, isInfinity, signbit;
|
import std.math.traits : isNaN, isInfinity, signbit;
|
||||||
import std.math.constants : LN2;
|
import std.math.constants : LN2;
|
||||||
|
|
||||||
|
@ -3259,7 +3258,7 @@ real log1p(real x) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
// On x87, yl2xp1 is valid if and only if -0.5 <= lg(x) <= 0.5,
|
// On x87, yl2xp1 is valid if and only if -0.5 <= lg(x) <= 0.5,
|
||||||
// ie if -0.29 <= x <= 0.414
|
// ie if -0.29 <= x <= 0.414
|
||||||
return (fabs(x) <= 0.25) ? core.math.yl2xp1(x, LN2) : core.math.yl2x(x+1, LN2);
|
return (core.math.fabs(x) <= 0.25) ? core.math.yl2xp1(x, LN2) : core.math.yl2x(x+1, LN2);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
|
|
@ -866,7 +866,7 @@ int feqrel(X)(const X x, const X y) @trusted pure nothrow @nogc
|
||||||
if (isFloatingPoint!(X))
|
if (isFloatingPoint!(X))
|
||||||
{
|
{
|
||||||
import std.math : floatTraits, RealFormat;
|
import std.math : floatTraits, RealFormat;
|
||||||
import std.math.algebraic : fabs;
|
import core.math : fabs;
|
||||||
|
|
||||||
/* Public Domain. Author: Don Clugston, 18 Aug 2005.
|
/* Public Domain. Author: Don Clugston, 18 Aug 2005.
|
||||||
*/
|
*/
|
||||||
|
@ -1035,7 +1035,7 @@ if (isFloatingPoint!(X))
|
||||||
deprecated("approxEqual will be removed in 2.106.0. Please use isClose instead.")
|
deprecated("approxEqual will be removed in 2.106.0. Please use isClose instead.")
|
||||||
bool approxEqual(T, U, V)(T value, U reference, V maxRelDiff = 1e-2, V maxAbsDiff = 1e-5)
|
bool approxEqual(T, U, V)(T value, U reference, V maxRelDiff = 1e-2, V maxAbsDiff = 1e-5)
|
||||||
{
|
{
|
||||||
import std.math.algebraic : fabs;
|
import core.math : fabs;
|
||||||
import std.range.primitives : empty, front, isInputRange, popFront;
|
import std.range.primitives : empty, front, isInputRange, popFront;
|
||||||
static if (isInputRange!T)
|
static if (isInputRange!T)
|
||||||
{
|
{
|
||||||
|
@ -1725,7 +1725,7 @@ if (isFloatingPoint!T)
|
||||||
{
|
{
|
||||||
if (__ctfe)
|
if (__ctfe)
|
||||||
{
|
{
|
||||||
import std.math.algebraic : abs, fabs;
|
import core.math : fabs;
|
||||||
import std.math.rounding : floor;
|
import std.math.rounding : floor;
|
||||||
import std.math.traits : isInfinity, isNaN;
|
import std.math.traits : isInfinity, isNaN;
|
||||||
import std.math.exponential : log2;
|
import std.math.exponential : log2;
|
||||||
|
@ -1737,7 +1737,7 @@ if (isFloatingPoint!T)
|
||||||
else if (fabs(val) >= nextUp(real.max / 2))
|
else if (fabs(val) >= nextUp(real.max / 2))
|
||||||
ret.exponent = 32766;
|
ret.exponent = 32766;
|
||||||
else
|
else
|
||||||
ret.exponent = cast(int) (val.abs.log2.floor() + 16383);
|
ret.exponent = cast(int) (val.fabs.log2.floor() + 16383);
|
||||||
|
|
||||||
if (ret.exponent == 32767)
|
if (ret.exponent == 32767)
|
||||||
{
|
{
|
||||||
|
@ -1760,13 +1760,13 @@ if (isFloatingPoint!T)
|
||||||
val *= 2.0L ^^ delta;
|
val *= 2.0L ^^ delta;
|
||||||
}
|
}
|
||||||
|
|
||||||
ulong tmp = cast(ulong) abs(val);
|
ulong tmp = cast(ulong) fabs(val);
|
||||||
if (ret.exponent != 32767 && ret.exponent > 0 && tmp <= ulong.max / 2)
|
if (ret.exponent != 32767 && ret.exponent > 0 && tmp <= ulong.max / 2)
|
||||||
{
|
{
|
||||||
// correction, due to log2(val) being rounded up:
|
// correction, due to log2(val) being rounded up:
|
||||||
ret.exponent--;
|
ret.exponent--;
|
||||||
val *= 2;
|
val *= 2;
|
||||||
tmp = cast(ulong) abs(val);
|
tmp = cast(ulong) fabs(val);
|
||||||
}
|
}
|
||||||
|
|
||||||
ret.mantissa = tmp & ((1L << 63) - 1);
|
ret.mantissa = tmp & ((1L << 63) - 1);
|
||||||
|
|
|
@ -739,7 +739,7 @@ auto round(real x) @trusted nothrow @nogc
|
||||||
FloatingPointControl.setControlState(
|
FloatingPointControl.setControlState(
|
||||||
(old & (-1 - FloatingPointControl.roundingMask)) | FloatingPointControl.roundToZero
|
(old & (-1 - FloatingPointControl.roundingMask)) | FloatingPointControl.roundToZero
|
||||||
);
|
);
|
||||||
x = rint((x >= 0) ? x + 0.5 : x - 0.5);
|
x = core.math.rint((x >= 0) ? x + 0.5 : x - 0.5);
|
||||||
FloatingPointControl.setControlState(old);
|
FloatingPointControl.setControlState(old);
|
||||||
return x;
|
return x;
|
||||||
}
|
}
|
||||||
|
|
|
@ -553,7 +553,7 @@ private T tanImpl(T)(T x) @safe pure nothrow @nogc
|
||||||
*/
|
*/
|
||||||
real acos(real x) @safe pure nothrow @nogc
|
real acos(real x) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
import std.math.algebraic : sqrt;
|
import core.math : sqrt;
|
||||||
|
|
||||||
return atan2(sqrt(1-x*x), x);
|
return atan2(sqrt(1-x*x), x);
|
||||||
}
|
}
|
||||||
|
@ -597,7 +597,7 @@ float acos(float x) @safe pure nothrow @nogc { return acos(cast(real) x); }
|
||||||
*/
|
*/
|
||||||
real asin(real x) @safe pure nothrow @nogc
|
real asin(real x) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
import std.math.algebraic : sqrt;
|
import core.math : sqrt;
|
||||||
|
|
||||||
return atan2(x, sqrt(1-x*x));
|
return atan2(x, sqrt(1-x*x));
|
||||||
}
|
}
|
||||||
|
@ -1181,7 +1181,7 @@ private F _sinh(F)(F x)
|
||||||
{
|
{
|
||||||
import std.math.traits : copysign;
|
import std.math.traits : copysign;
|
||||||
import std.math.exponential : exp, expm1;
|
import std.math.exponential : exp, expm1;
|
||||||
import std.math.algebraic : fabs;
|
import core.math : fabs;
|
||||||
import std.math.constants : LN2;
|
import std.math.constants : LN2;
|
||||||
|
|
||||||
// sinh(x) = (exp(x)-exp(-x))/2;
|
// sinh(x) = (exp(x)-exp(-x))/2;
|
||||||
|
@ -1235,7 +1235,7 @@ private F _tanh(F)(F x)
|
||||||
{
|
{
|
||||||
import std.math.traits : copysign;
|
import std.math.traits : copysign;
|
||||||
import std.math.exponential : expm1;
|
import std.math.exponential : expm1;
|
||||||
import std.math.algebraic : fabs;
|
import core.math : fabs;
|
||||||
import std.math.constants : LN2;
|
import std.math.constants : LN2;
|
||||||
|
|
||||||
// tanh(x) = (exp(x) - exp(-x))/(exp(x)+exp(-x))
|
// tanh(x) = (exp(x) - exp(-x))/(exp(x)+exp(-x))
|
||||||
|
@ -1297,7 +1297,7 @@ private F _acosh(F)(F x) @safe pure nothrow @nogc
|
||||||
{
|
{
|
||||||
import std.math.constants : LN2;
|
import std.math.constants : LN2;
|
||||||
import std.math.exponential : log;
|
import std.math.exponential : log;
|
||||||
import std.math.algebraic : sqrt;
|
import core.math : sqrt;
|
||||||
|
|
||||||
if (x > 1/F.epsilon)
|
if (x > 1/F.epsilon)
|
||||||
return F(LN2) + log(x);
|
return F(LN2) + log(x);
|
||||||
|
@ -1351,7 +1351,7 @@ float asinh(float x) @safe pure nothrow @nogc { return _asinh(x); }
|
||||||
private F _asinh(F)(F x)
|
private F _asinh(F)(F x)
|
||||||
{
|
{
|
||||||
import std.math.traits : copysign;
|
import std.math.traits : copysign;
|
||||||
import std.math.algebraic : fabs, sqrt;
|
import core.math : fabs, sqrt;
|
||||||
import std.math.exponential : log, log1p;
|
import std.math.exponential : log, log1p;
|
||||||
import std.math.constants : LN2;
|
import std.math.constants : LN2;
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue