summaryrefslogtreecommitdiff
path: root/numpy
diff options
context:
space:
mode:
Diffstat (limited to 'numpy')
-rw-r--r--numpy/add_newdocs.py31
-rw-r--r--numpy/core/src/multiarray/_multiarray_tests.c.src63
2 files changed, 93 insertions, 1 deletions
diff --git a/numpy/add_newdocs.py b/numpy/add_newdocs.py
index fc2130096..9372b3431 100644
--- a/numpy/add_newdocs.py
+++ b/numpy/add_newdocs.py
@@ -5607,6 +5607,37 @@ add_newdoc('numpy.core.multiarray', 'unpackbits',
""")
+add_newdoc('numpy.core._multiarray_tests', 'format_float_OSprintf_g',
+ """
+ format_float_OSprintf_g(val, precision)
+
+ Print a floating point scalar using the system's printf function,
+ equivalent to:
+
+ printf("%.*g", precision, val);
+
+ for half/float/double, or replacing 'g' by 'Lg' for longdouble. This
+ method is designed to help cross-validate the format_float_* methods.
+
+ Parameters
+ ----------
+ val : python float or numpy floating scalar
+ Value to format.
+
+ precision : non-negative integer, optional
+ Precision given to printf.
+
+ Returns
+ -------
+ rep : string
+ The string representation of the floating point value
+
+ See Also
+ --------
+ format_float_scientific
+ format_float_positional
+ """)
+
##############################################################################
#
diff --git a/numpy/core/src/multiarray/_multiarray_tests.c.src b/numpy/core/src/multiarray/_multiarray_tests.c.src
index 0299f1a1b..cba96a4c2 100644
--- a/numpy/core/src/multiarray/_multiarray_tests.c.src
+++ b/numpy/core/src/multiarray/_multiarray_tests.c.src
@@ -3,7 +3,9 @@
#include <Python.h>
#define _NPY_NO_DEPRECATIONS /* for NPY_CHAR */
#include "numpy/arrayobject.h"
+#include "numpy/arrayscalars.h"
#include "numpy/npy_math.h"
+#include "numpy/halffloat.h"
#include "mem_overlap.h"
#include "npy_extint128.h"
#include "common.h"
@@ -1828,6 +1830,63 @@ call_npy_@name@@suffix@(PyObject *NPY_UNUSED(self), PyObject *args)
/**end repeat**/
+/*
+ * For development/testing purposes, it's convenient to have access to the
+ * system printf for floats. This is a very simple printf interface.
+ */
+PyObject *
+PrintFloat_Printf_g(PyObject *obj, int precision)
+{
+ char str[1024];
+
+ if (PyArray_IsScalar(obj, Half)) {
+ npy_half x = ((PyHalfScalarObject *)obj)->obval;
+ PyOS_snprintf(str, sizeof(str), "%.*g", precision,
+ npy_half_to_double(x));
+ }
+ else if (PyArray_IsScalar(obj, Float)) {
+ npy_float x = ((PyFloatScalarObject *)obj)->obval;
+ PyOS_snprintf(str, sizeof(str), "%.*g", precision, x);
+ }
+ else if (PyArray_IsScalar(obj, Double)) {
+ npy_double x = ((PyDoubleScalarObject *)obj)->obval;
+ PyOS_snprintf(str, sizeof(str), "%.*g", precision, x);
+ /* would be better to use lg, but not available in C90 */
+ }
+ else if (PyArray_IsScalar(obj, LongDouble)) {
+ npy_longdouble x = ((PyLongDoubleScalarObject *)obj)->obval;
+ PyOS_snprintf(str, sizeof(str), "%.*Lg", precision, x);
+ }
+ else{
+ double val = PyFloat_AsDouble(obj);
+ if (error_converting(val)) {
+ return NULL;
+ }
+ PyOS_snprintf(str, sizeof(str), "%.*g", precision, val);
+ }
+
+ return PyUString_FromString(str);
+}
+
+
+static PyObject *
+printf_float_g(PyObject *NPY_UNUSED(dummy), PyObject *args, PyObject *kwds)
+{
+ PyObject *obj;
+ int precision;
+
+ if (!PyArg_ParseTuple(args,"Oi:format_float_OSprintf_g", &obj,
+ &precision)) {
+ return NULL;
+ }
+
+ if (precision < 0) {
+ PyErr_SetString(PyExc_TypeError, "precision must be non-negative");
+ return NULL;
+ }
+
+ return PrintFloat_Printf_g(obj, precision);
+}
static PyMethodDef Multiarray_TestsMethods[] = {
{"IsPythonScalar",
@@ -1967,7 +2026,9 @@ static PyMethodDef Multiarray_TestsMethods[] = {
/**end repeat1**/
/**end repeat**/
-
+ {"format_float_OSprintf_g",
+ (PyCFunction)printf_float_g,
+ METH_VARARGS , NULL},
{NULL, NULL, 0, NULL} /* Sentinel */
};