Commit 70932b0e authored by Christian Heimes's avatar Christian Heimes

Now that I've learnt about structseq objects I felt like converting...

Now that I've learnt about structseq objects I felt like converting sys.float_info to a structseq. It's
readonly and help(sys.float_info) explains the attributes nicely.
parent 5ed10d78
...@@ -559,7 +559,7 @@ Floating Point Objects ...@@ -559,7 +559,7 @@ Floating Point Objects
.. cfunction:: PyObject* PyFloat_GetInfo(void) .. cfunction:: PyObject* PyFloat_GetInfo(void)
Return a :ctype:`PyDictObject` object which contains information about the Return a structseq instance which contains information about the
precision, minimum and maximum values of a float. It's a thin wrapper precision, minimum and maximum values of a float. It's a thin wrapper
around the header file :file:`float.h`. around the header file :file:`float.h`.
......
...@@ -280,12 +280,12 @@ always available. ...@@ -280,12 +280,12 @@ always available.
.. data:: float_info .. data:: float_info
A dict holding information about the float type. It contains low level A structseq holding information about the float type. It contains low level
information about the precision and internal representation. Please study information about the precision and internal representation. Please study
your system's :file:`float.h` for more information. your system's :file:`float.h` for more information.
+---------------------+--------------------------------------------------+ +---------------------+--------------------------------------------------+
| key | explanation | | attribute | explanation |
+=====================+==================================================+ +=====================+==================================================+
| :const:`epsilon` | Difference between 1 and the next representable | | :const:`epsilon` | Difference between 1 and the next representable |
| | floating point number | | | floating point number |
......
...@@ -329,8 +329,8 @@ class SysModuleTest(unittest.TestCase): ...@@ -329,8 +329,8 @@ class SysModuleTest(unittest.TestCase):
self.assert_(isinstance(sys.copyright, basestring)) self.assert_(isinstance(sys.copyright, basestring))
self.assert_(isinstance(sys.exec_prefix, basestring)) self.assert_(isinstance(sys.exec_prefix, basestring))
self.assert_(isinstance(sys.executable, basestring)) self.assert_(isinstance(sys.executable, basestring))
self.assert_(isinstance(sys.float_info, dict))
self.assertEqual(len(sys.float_info), 11) self.assertEqual(len(sys.float_info), 11)
self.assertEqual(sys.float_info.radix, 2)
self.assert_(isinstance(sys.hexversion, int)) self.assert_(isinstance(sys.hexversion, int))
self.assert_(isinstance(sys.maxint, int)) self.assert_(isinstance(sys.maxint, int))
if test.test_support.have_unicode: if test.test_support.have_unicode:
......
...@@ -12,6 +12,9 @@ What's New in Python 2.6 alpha 1? ...@@ -12,6 +12,9 @@ What's New in Python 2.6 alpha 1?
Core and builtins Core and builtins
----------------- -----------------
- sys.float_info / PyFloat_GetInfo: The floating point information
object was converted from a dict to a specialized structseq object.
- Patch #1816: Added sys.flags structseq. It exposes the status of most - Patch #1816: Added sys.flags structseq. It exposes the status of most
command line arguments and PYTHON* environment variables. command line arguments and PYTHON* environment variables.
......
...@@ -5,10 +5,12 @@ ...@@ -5,10 +5,12 @@
for any kind of float exception without losing portability. */ for any kind of float exception without losing portability. */
#include "Python.h" #include "Python.h"
#include "structseq.h"
#include <ctype.h> #include <ctype.h>
#include <float.h> #include <float.h>
#if !defined(__STDC__) #if !defined(__STDC__)
extern double fmod(double, double); extern double fmod(double, double);
extern double pow(double, double); extern double pow(double, double);
...@@ -59,39 +61,86 @@ PyFloat_GetMin(void) ...@@ -59,39 +61,86 @@ PyFloat_GetMin(void)
return DBL_MIN; return DBL_MIN;
} }
static PyTypeObject FloatInfoType = {0};
PyDoc_STRVAR(floatinfo__doc__,
"sys.floatinfo\n\
\n\
A structseq holding information about the float type. It contains low level\n\
information about the precision and internal representation. Please study\n\
your system's :file:`float.h` for more information.");
static PyStructSequence_Field floatinfo_fields[] = {
{"max", "DBL_MAX -- maximum representable finite float"},
{"max_exp", "DBL_MAX_EXP -- maximum int e such that radix**(e-1) "
"is representable"},
{"max_10_exp", "DBL_MAX_10_EXP -- maximum int e such that 10**e "
"is representable"},
{"min", "DBL_MIN -- Minimum positive normalizer float"},
{"min_exp", "DBL_MIN_EXP -- minimum int e such that radix**(e-1) "
"is a normalized float"},
{"min_10_exp", "DBL_MIN_10_EXP -- minimum int e such that 10**e is "
"a normalized"},
{"dig", "DBL_DIG -- digits"},
{"mant_dig", "DBL_MANT_DIG -- mantissa digits"},
{"epsilon", "DBL_EPSILON -- Difference between 1 and the next "
"representable float"},
{"radix", "FLT_RADIX -- radix of exponent"},
{"rounds", "FLT_ROUNDS -- addition rounds"},
{0}
};
static PyStructSequence_Desc floatinfo_desc = {
"sys.floatinfo", /* name */
floatinfo__doc__, /* doc */
floatinfo_fields, /* fields */
11
};
PyObject * PyObject *
PyFloat_GetInfo(void) PyFloat_GetInfo(void)
{ {
PyObject *d, *tmp; static PyObject* floatinfo;
int pos = 0;
#define SET_FLOAT_CONST(d, key, const) \
tmp = PyFloat_FromDouble(const); \ if (floatinfo != NULL) {
if (tmp == NULL) return NULL; \ Py_INCREF(floatinfo);
if (PyDict_SetItemString(d, key, tmp)) return NULL; \ return floatinfo;
Py_DECREF(tmp) }
#define SET_INT_CONST(d, key, const) \ PyStructSequence_InitType(&FloatInfoType, &floatinfo_desc);
tmp = PyInt_FromLong(const); \
if (tmp == NULL) return NULL; \ floatinfo = PyStructSequence_New(&FloatInfoType);
if (PyDict_SetItemString(d, key, tmp)) return NULL; \ if (floatinfo == NULL) {
Py_DECREF(tmp) return NULL;
}
d = PyDict_New();
SET_FLOAT_CONST(d, "max", DBL_MAX);
SET_INT_CONST(d, "max_exp", DBL_MAX_EXP);
SET_INT_CONST(d, "max_10_exp", DBL_MAX_10_EXP);
SET_FLOAT_CONST(d, "min", DBL_MIN);
SET_INT_CONST(d, "min_exp", DBL_MIN_EXP);
SET_INT_CONST(d, "min_10_exp", DBL_MIN_10_EXP);
SET_INT_CONST(d, "dig", DBL_DIG);
SET_INT_CONST(d, "mant_dig", DBL_MANT_DIG);
SET_FLOAT_CONST(d, "epsilon", DBL_EPSILON);
SET_INT_CONST(d, "radix", FLT_RADIX);
SET_INT_CONST(d, "rounds", FLT_ROUNDS);
return d;
}
#define SetIntFlag(flag) \
PyStructSequence_SET_ITEM(floatinfo, pos++, PyInt_FromLong(flag))
#define SetDblFlag(flag) \
PyStructSequence_SET_ITEM(floatinfo, pos++, PyFloat_FromDouble(flag))
SetDblFlag(DBL_MAX);
SetIntFlag(DBL_MAX_EXP);
SetIntFlag(DBL_MAX_10_EXP);
SetDblFlag(DBL_MIN);
SetIntFlag(DBL_MIN_EXP);
SetIntFlag(DBL_MIN_10_EXP);
SetIntFlag(DBL_DIG);
SetIntFlag(DBL_MANT_DIG);
SetDblFlag(DBL_EPSILON);
SetIntFlag(FLT_RADIX);
SetIntFlag(FLT_ROUNDS);
#undef SetIntFlag
#undef SetDblFlag
if (PyErr_Occurred()) {
Py_CLEAR(floatinfo);
return NULL;
}
Py_INCREF(floatinfo);
return floatinfo;
}
PyObject * PyObject *
PyFloat_FromDouble(double fval) PyFloat_FromDouble(double fval)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment