[Numpy-svn] r6341 - in trunk/numpy/lib: . tests

numpy-svn@scip... numpy-svn@scip...
Wed Feb 4 22:31:55 CST 2009


Author: pierregm
Date: 2009-02-04 22:31:51 -0600 (Wed, 04 Feb 2009)
New Revision: 6341

Modified:
   trunk/numpy/lib/_iotools.py
   trunk/numpy/lib/io.py
   trunk/numpy/lib/tests/test__iotools.py
   trunk/numpy/lib/tests/test_io.py
Log:
*  genfromtxt : Fixed when a dtype involving objects is explicitly given. Raise a NotImplementedError if the dtype is nested.
* _iotools : make sure StringConverter gets properly initiated when a function returning a np.object is used as input parameter.

Modified: trunk/numpy/lib/_iotools.py
===================================================================
--- trunk/numpy/lib/_iotools.py	2009-02-04 21:53:05 UTC (rev 6340)
+++ trunk/numpy/lib/_iotools.py	2009-02-05 04:31:51 UTC (rev 6341)
@@ -54,6 +54,16 @@
     return fhd
 
 
+def has_nested_fields(ndtype):
+    """
+    Returns whether one or several fields of a structured array are nested.
+    """
+    for name in ndtype.names or ():
+        if ndtype[name].names:
+            return True
+    return False
+
+
 def flatten_dtype(ndtype):
     """
     Unpack a structured data-type.
@@ -71,7 +81,6 @@
         return types
 
 
-
 class LineSplitter:
     """
     Defines a function to split a string at a given delimiter or at given places.
@@ -377,11 +386,17 @@
                         default = None
                 ttype = self._getsubdtype(default)
             # Set the status according to the dtype
+            _status = -1
             for (i, (deftype, func, default_def)) in enumerate(self._mapper):
                 if np.issubdtype(ttype, deftype):
-                    self._status = i
+                    _status = i
                     self.default = default or default_def
                     break
+            if _status == -1:
+                # We never found a match in the _mapper...
+                _status = 0
+                self.default = default
+            self._status = _status
             # If the input was a dtype, set the function to the last we saw
             if self.func is None:
                 self.func = func

Modified: trunk/numpy/lib/io.py
===================================================================
--- trunk/numpy/lib/io.py	2009-02-04 21:53:05 UTC (rev 6340)
+++ trunk/numpy/lib/io.py	2009-02-05 04:31:51 UTC (rev 6341)
@@ -17,7 +17,7 @@
 from _compiled_base import packbits, unpackbits
 
 from _iotools import LineSplitter, NameValidator, StringConverter, \
-                     _is_string_like, flatten_dtype
+                     _is_string_like, has_nested_fields, flatten_dtype
 
 _file = file
 _string_like = _is_string_like
@@ -703,6 +703,11 @@
       there must not be any header in the file (else a :exc:ValueError exception
       is raised).
 
+    Warnings
+    --------
+    * Individual values are not stripped of spaces by default.
+      When using a custom converter, make sure the function does remove spaces.
+
     See Also
     --------
     numpy.loadtxt : equivalent function when no data is missing.
@@ -918,8 +923,15 @@
             # First, create the array using a flattened dtype:
             # [('a', int), ('b1', int), ('b2', float)]
             # Then, view the array using the specified dtype.
-            rows = np.array(data, dtype=[('', t) for t in flatdtypes])
-            output = rows.view(dtype)
+            if has_nested_fields(dtype):
+                if 'O' in (_.char for _ in flatdtypes):
+                    errmsg = "Nested fields involving objects "\
+                             "are not supported..."
+                    raise NotImplementedError(errmsg)
+                rows = np.array(data, dtype=[('', t) for t in flatdtypes])
+                output = rows.view(dtype)
+            else:
+                output = np.array(data, dtype=dtype)
             # Now, process the rowmasks the same way
             if usemask:
                 rowmasks = np.array(masks,

Modified: trunk/numpy/lib/tests/test__iotools.py
===================================================================
--- trunk/numpy/lib/tests/test__iotools.py	2009-02-04 21:53:05 UTC (rev 6340)
+++ trunk/numpy/lib/tests/test__iotools.py	2009-02-05 04:31:51 UTC (rev 6341)
@@ -2,7 +2,8 @@
 import StringIO
 
 import numpy as np
-from numpy.lib._iotools import LineSplitter, NameValidator, StringConverter
+from numpy.lib._iotools import LineSplitter, NameValidator, StringConverter,\
+                               has_nested_fields
 from numpy.testing import *
 
 class TestLineSplitter(TestCase):
@@ -142,3 +143,17 @@
         test = convert('')
         assert_equal(test, date(2000, 01, 01))
 
+
+#-------------------------------------------------------------------------------
+
+class TestMiscFunctions(TestCase):
+    #
+    def test_has_nested_dtype(self):
+        "Test has_nested_dtype"
+        ndtype = np.dtype(np.float)
+        assert_equal(has_nested_fields(ndtype), False)
+        ndtype = np.dtype([('A', '|S3'), ('B', float)])
+        assert_equal(has_nested_fields(ndtype), False)
+        ndtype = np.dtype([('A', int), ('B', [('BA', float), ('BB', '|S1')])])
+        assert_equal(has_nested_fields(ndtype), True)
+

Modified: trunk/numpy/lib/tests/test_io.py
===================================================================
--- trunk/numpy/lib/tests/test_io.py	2009-02-04 21:53:05 UTC (rev 6340)
+++ trunk/numpy/lib/tests/test_io.py	2009-02-05 04:31:51 UTC (rev 6341)
@@ -573,6 +573,35 @@
         assert_equal(test, control)
 
 
+    def test_dtype_with_object(self):
+        "Test using an explicit dtype qith an object"
+        from datetime import date
+        import time
+        data = """
+        1; 2001-01-01
+        2; 2002-01-31
+        """
+        ndtype = [('idx', int), ('code', np.object)]
+        func = lambda s: date(*(time.strptime(s.strip(), "%Y-%m-%d")[:3]))
+        converters = {1: func}
+        test = np.genfromtxt(StringIO.StringIO(data), delimiter=";", dtype=ndtype,
+                             converters=converters)
+        control = np.array([(1, date(2001,1,1)), (2, date(2002,1,31))],
+                           dtype=ndtype)
+        assert_equal(test, control)
+        #
+        ndtype = [('nest', [('idx', int), ('code', np.object)])]
+        try:
+            test = np.genfromtxt(StringIO.StringIO(data), delimiter=";",
+                                 dtype=ndtype, converters=converters)
+        except NotImplementedError:
+            pass
+        else:
+            errmsg = "Nested dtype involving objects should be supported."
+            raise AssertionError(errmsg)
+        
+
+
     def test_spacedelimiter(self):
         "Test space delimiter"
         data = StringIO.StringIO("1  2  3  4   5\n6  7  8  9  10")



More information about the Numpy-svn mailing list