Skip to content

Commit 439380e

Browse files
committed
gh-73487: convert the _decimal module to use AC
1 parent 046a4e3 commit 439380e

File tree

7 files changed

+257
-56
lines changed

7 files changed

+257
-56
lines changed

Include/internal/pycore_global_objects_fini_generated.h

Lines changed: 2 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Include/internal/pycore_global_strings.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -640,6 +640,7 @@ struct _Py_global_strings {
640640
STRUCT_FOR_ID(options)
641641
STRUCT_FOR_ID(order)
642642
STRUCT_FOR_ID(origin)
643+
STRUCT_FOR_ID(other)
643644
STRUCT_FOR_ID(out_fd)
644645
STRUCT_FOR_ID(outgoing)
645646
STRUCT_FOR_ID(outpath)
@@ -695,6 +696,7 @@ struct _Py_global_strings {
695696
STRUCT_FOR_ID(return)
696697
STRUCT_FOR_ID(reverse)
697698
STRUCT_FOR_ID(reversed)
699+
STRUCT_FOR_ID(rounding)
698700
STRUCT_FOR_ID(salt)
699701
STRUCT_FOR_ID(sched_priority)
700702
STRUCT_FOR_ID(scheduler)

Include/internal/pycore_runtime_init_generated.h

Lines changed: 2 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Include/internal/pycore_unicodeobject_generated.h

Lines changed: 8 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Modules/_decimal/_decimal.c

Lines changed: 66 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,14 @@
5858
#define _PY_DEC_ROUND_GUARD (MPD_ROUND_GUARD-1)
5959
#endif
6060

61+
#include "clinic/_decimal.c.h"
62+
63+
/*[clinic input]
64+
module _decimal
65+
class _decimal.Decimal "PyObject *" "&dec_spec"
66+
[clinic start generated code]*/
67+
/*[clinic end generated code: output=da39a3ee5e6b4b0d input=e0e1f68f1f413f5f]*/
68+
6169
struct PyDecContextObject;
6270
struct DecCondMap;
6371

@@ -4648,20 +4656,33 @@ dec_mpd_to_eng(PyObject *self, PyObject *args, PyObject *kwds)
46484656
Dec_BinaryFuncVA_NO_CTX(mpd_compare_total)
46494657
Dec_BinaryFuncVA_NO_CTX(mpd_compare_total_mag)
46504658

4659+
/*[clinic input]
4660+
_decimal.Decimal.copy_sign
4661+
4662+
other: object
4663+
context: object = None
4664+
4665+
Returns self with the sign of other.
4666+
4667+
For example:
4668+
4669+
>>> Decimal('2.3').copy_sign(Decimal('-1.5'))
4670+
Decimal('-2.3')
4671+
4672+
This operation is unaffected by context and is quiet: no flags are changed
4673+
and no rounding is performed. As an exception, the C version may raise
4674+
InvalidOperation if the second operand cannot be converted exactly.
4675+
[clinic start generated code]*/
4676+
46514677
static PyObject *
4652-
dec_mpd_qcopy_sign(PyObject *self, PyObject *args, PyObject *kwds)
4678+
_decimal_Decimal_copy_sign_impl(PyObject *self, PyObject *other,
4679+
PyObject *context)
4680+
/*[clinic end generated code: output=72c62177763e012e input=f02ebb5d7489c502]*/
46534681
{
4654-
static char *kwlist[] = {"other", "context", NULL};
4655-
PyObject *other;
46564682
PyObject *a, *b;
46574683
PyObject *result;
4658-
PyObject *context = Py_None;
46594684
uint32_t status = 0;
46604685

4661-
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O", kwlist,
4662-
&other, &context)) {
4663-
return NULL;
4664-
}
46654686
decimal_state *state = get_module_state_by_def(Py_TYPE(self));
46664687
CONTEXT_CHECK_VA(state, context);
46674688
CONVERT_BINOP_RAISE(&a, &b, self, other, context);
@@ -4717,22 +4738,46 @@ Dec_BinaryFuncVA(mpd_qrotate)
47174738
Dec_BinaryFuncVA(mpd_qscaleb)
47184739
Dec_BinaryFuncVA(mpd_qshift)
47194740

4741+
/*[clinic input]
4742+
_decimal.Decimal.quantize
4743+
4744+
exp as w: object
4745+
rounding: object = None
4746+
context: object = None
4747+
4748+
Quantize self so its exponent is the same as that of exp.
4749+
4750+
Return a value equal to the first operand after rounding and having the
4751+
exponent of the second operand.
4752+
4753+
>>> Decimal('1.41421356').quantize(Decimal('1.000'))
4754+
Decimal('1.414')
4755+
4756+
Unlike other operations, if the length of the coefficient after the quantize
4757+
operation would be greater than precision, then an InvalidOperation is signaled.
4758+
This guarantees that, unless there is an error condition, the quantized exponent
4759+
is always equal to that of the right-hand operand.
4760+
4761+
Also unlike other operations, quantize never signals Underflow, even if the
4762+
result is subnormal and inexact.
4763+
4764+
If the exponent of the second operand is larger than that of the first, then
4765+
rounding may be necessary. In this case, the rounding mode is determined by the
4766+
rounding argument if given, else by the given context argument; if neither
4767+
argument is given, the rounding mode of the current thread's context is used.
4768+
[clinic start generated code]*/
4769+
47204770
static PyObject *
4721-
dec_mpd_qquantize(PyObject *v, PyObject *args, PyObject *kwds)
4771+
_decimal_Decimal_quantize_impl(PyObject *self, PyObject *w,
4772+
PyObject *rounding, PyObject *context)
4773+
/*[clinic end generated code: output=5e84581f96dc685c input=eed2fdd8d65fce21]*/
47224774
{
4723-
static char *kwlist[] = {"exp", "rounding", "context", NULL};
4724-
PyObject *rounding = Py_None;
4725-
PyObject *context = Py_None;
4726-
PyObject *w, *a, *b;
4775+
PyObject *a, *b;
47274776
PyObject *result;
47284777
uint32_t status = 0;
47294778
mpd_context_t workctx;
47304779

4731-
if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|OO", kwlist,
4732-
&w, &rounding, &context)) {
4733-
return NULL;
4734-
}
4735-
decimal_state *state = get_module_state_by_def(Py_TYPE(v));
4780+
decimal_state *state = get_module_state_by_def(Py_TYPE(self));
47364781
CONTEXT_CHECK_VA(state, context);
47374782

47384783
workctx = *CTX(context);
@@ -4746,7 +4791,7 @@ dec_mpd_qquantize(PyObject *v, PyObject *args, PyObject *kwds)
47464791
}
47474792
}
47484793

4749-
CONVERT_BINOP_RAISE(&a, &b, v, w, context);
4794+
CONVERT_BINOP_RAISE(&a, &b, self, w, context);
47504795

47514796
result = dec_alloc(state);
47524797
if (result == NULL) {
@@ -5094,7 +5139,7 @@ static PyMethodDef dec_methods [] =
50945139
{ "min", _PyCFunction_CAST(dec_mpd_qmin), METH_VARARGS|METH_KEYWORDS, doc_min },
50955140
{ "min_mag", _PyCFunction_CAST(dec_mpd_qmin_mag), METH_VARARGS|METH_KEYWORDS, doc_min_mag },
50965141
{ "next_toward", _PyCFunction_CAST(dec_mpd_qnext_toward), METH_VARARGS|METH_KEYWORDS, doc_next_toward },
5097-
{ "quantize", _PyCFunction_CAST(dec_mpd_qquantize), METH_VARARGS|METH_KEYWORDS, doc_quantize },
5142+
_DECIMAL_DECIMAL_QUANTIZE_METHODDEF
50985143
{ "remainder_near", _PyCFunction_CAST(dec_mpd_qrem_near), METH_VARARGS|METH_KEYWORDS, doc_remainder_near },
50995144

51005145
/* Ternary arithmetic functions, optional context arg */
@@ -5133,7 +5178,7 @@ static PyMethodDef dec_methods [] =
51335178
/* Binary functions, optional context arg for conversion errors */
51345179
{ "compare_total", _PyCFunction_CAST(dec_mpd_compare_total), METH_VARARGS|METH_KEYWORDS, doc_compare_total },
51355180
{ "compare_total_mag", _PyCFunction_CAST(dec_mpd_compare_total_mag), METH_VARARGS|METH_KEYWORDS, doc_compare_total_mag },
5136-
{ "copy_sign", _PyCFunction_CAST(dec_mpd_qcopy_sign), METH_VARARGS|METH_KEYWORDS, doc_copy_sign },
5181+
_DECIMAL_DECIMAL_COPY_SIGN_METHODDEF
51375182
{ "same_quantum", _PyCFunction_CAST(dec_mpd_same_quantum), METH_VARARGS|METH_KEYWORDS, doc_same_quantum },
51385183

51395184
/* Binary functions, optional context arg */

Modules/_decimal/clinic/_decimal.c.h

Lines changed: 177 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)