@@ -423,6 +423,12 @@ def __new__(subtype, shape, dtype=None, buf=None, offset=0, strides=None,
423423 strides = strides , order = order )
424424 return self
425425
426+ def __array_finalize__ (self , obj ):
427+ if self .dtype .type is not record :
428+ # if self.dtype is not np.record, invoke __setattr__ which will
429+ # convert it to a record if it is a void dtype.
430+ self .dtype = self .dtype
431+
426432 def __getattribute__ (self , attr ):
427433 # See if ndarray has this attr, and return it if so. (note that this
428434 # means a field with the same name as an ndarray attr cannot be
@@ -456,6 +462,11 @@ def __getattribute__(self, attr):
456462 # Undo any "setting" of the attribute and do a setfield
457463 # Thus, you can't create attributes on-the-fly that are field names.
458464 def __setattr__ (self , attr , val ):
465+
466+ # Automatically convert (void) dtypes to records.
467+ if attr == 'dtype' and issubclass (val .type , nt .void ):
468+ val = sb .dtype ((record , val ))
469+
459470 newattr = attr not in self .__dict__
460471 try :
461472 ret = object .__setattr__ (self , attr , val )
@@ -502,8 +513,10 @@ def __repr__(self):
502513 # show zero-length shape unless it is (0,)
503514 lst = "[], shape=%s" % (repr (self .shape ),)
504515
505- if self .dtype .type is record :
516+ if (self .dtype .type is record
517+ or (not issubclass (self .dtype .type , nt .void )) ):
506518 # If this is a full record array (has numpy.record dtype),
519+ # or if it has a scalar (non-void) dtype with no records,
507520 # represent it using the rec.array function. Since rec.array
508521 # converts dtype to a numpy.record for us, use only dtype.descr,
509522 # not repr(dtype).
@@ -512,7 +525,8 @@ def __repr__(self):
512525 (lst , lf , repr (self .dtype .descr )))
513526 else :
514527 # otherwise represent it using np.array plus a view
515- # (There is currently (v1.10) no other easy way to create it)
528+ # This should only happen if the user is playing
529+ # strange games with dtypes.
516530 lf = '\n ' + ' ' * len ("array(" )
517531 return ('array(%s, %sdtype=%s).view(numpy.recarray)' %
518532 (lst , lf , str (self .dtype )))
@@ -534,22 +548,6 @@ def field(self, attr, val=None):
534548 else :
535549 return self .setfield (val , * res )
536550
537- def view (self , dtype = None , type = None ):
538- if dtype is None :
539- return ndarray .view (self , type )
540- elif type is None :
541- try :
542- if issubclass (dtype , ndarray ):
543- return ndarray .view (self , dtype )
544- except TypeError :
545- pass
546- dtype = sb .dtype (dtype )
547- if dtype .fields is None :
548- return self .__array__ ().view (dtype )
549- return ndarray .view (self , dtype )
550- else :
551- return ndarray .view (self , dtype , type )
552-
553551
554552def fromarrays (arrayList , dtype = None , shape = None , formats = None ,
555553 names = None , titles = None , aligned = False , byteorder = None ):
@@ -837,10 +835,7 @@ def array(obj, dtype=None, shape=None, offset=0, strides=None, formats=None,
837835 new = obj
838836 if copy :
839837 new = new .copy ()
840- res = new .view (recarray )
841- if issubclass (res .dtype .type , nt .void ):
842- res .dtype = sb .dtype ((record , res .dtype ))
843- return res
838+ return new .view (recarray )
844839
845840 else :
846841 interface = getattr (obj , "__array_interface__" , None )
@@ -849,7 +844,4 @@ def array(obj, dtype=None, shape=None, offset=0, strides=None, formats=None,
849844 obj = sb .array (obj )
850845 if dtype is not None and (obj .dtype != dtype ):
851846 obj = obj .view (dtype )
852- res = obj .view (recarray )
853- if issubclass (res .dtype .type , nt .void ):
854- res .dtype = sb .dtype ((record , res .dtype ))
855- return res
847+ return obj .view (recarray )
0 commit comments