@@ -29,6 +29,10 @@ def mp_constant(fn: str, d=None) -> mpmath.ctx_mp_python.mpf:
2929 if d is None :
3030 return getattr (mpmath , fn )()
3131 else :
32+ # TODO: In some function like Pi, you can
33+ # ask for a certain number of digits, but the
34+ # accuracy will be less than that. Figure out
35+ # what's up and compensate somehow.
3236 mpmath .mp .dps = int_d = int (d )
3337 return getattr (mpmath , fn )(prec = int_d )
3438
@@ -43,6 +47,9 @@ def mp_convert_constant(obj, **kwargs):
4347
4448
4549def numpy_constant (name : str , d = None ) -> float :
50+ # TODO: although numpy doesn't support arbitrary precision,
51+ # if d is smaller than the precision given we could *reduce* the
52+ # float returned.
4653 return getattr (numpy , name )
4754
4855
@@ -54,10 +61,17 @@ class _Constant_Common(Predefined):
5461
5562 attributes = ("Constant" , "Protected" , "ReadProtected" )
5663 nargs = 0
64+ options = {"Method" : "sympy" }
5765
58- def apply_N (self , precision , evaluation ):
59- "N[%(name)s, precision_]"
60- return self .get_constant (precision , evaluation )
66+ def apply_N (self , precision , evaluation , options = {}):
67+ "N[%(name)s, precision_?NumericQ, OptionsPattern[%(name)s]]"
68+
69+ preference = self .get_option (options , "Method" , evaluation ).get_string_value ()
70+ return self .get_constant (precision , evaluation , preference )
71+
72+ def apply_N2 (self , evaluation , options = {}):
73+ "N[%(name)s, OptionsPattern[%(name)s]]"
74+ return self .apply_N (None , evaluation , options )
6175
6276 def is_constant (self ) -> bool :
6377 return True
@@ -71,10 +85,12 @@ def get_constant(self, precision, evaluation, preference=None):
7185 .get_string_value ()
7286 )
7387 # TODO: validate PreferredBackendMethod is in "mpmath", "numpy", "sympy"
74- try :
75- d = get_precision (precision , evaluation )
76- except PrecisionValueError :
77- d = None
88+ d = None
89+ if precision :
90+ try :
91+ d = get_precision (precision , evaluation )
92+ except PrecisionValueError :
93+ pass
7894
7995 conversion_fn = MachineReal if d is None else PrecisionReal
8096
@@ -85,13 +101,15 @@ def get_constant(self, precision, evaluation, preference=None):
85101 elif preference == "mpmath" and hasattr (self , "mpmath_name" ):
86102 value = mp_constant (self .mpmath_name , d )
87103 elif preference == "numpy" and hasattr (self , "numpy_name" ):
88- value = numpy_constant (self .numpy_name )
104+ # Note numpy doesn't support arbitarary precision
105+ value = numpy_constant (self .numpy_name , d )
89106 elif hasattr (self , "mpmath_name" ):
90107 value = mp_constant (self .mpmath_name , d )
91108 elif hasattr (self , "sympy_name" ):
92109 value = sympy_constant (self .sympy_name , d )
93110 elif hasattr (self , "numpy_name" ):
94- value = numpy_constant (self .numpy_name )
111+ # Note numpy doesn't support arbitarary precision
112+ value = numpy_constant (self .numpy_name , d )
95113 return conversion_fn (value )
96114
97115
0 commit comments