docs: def describe(data, name, len_types={}, val_types={},
                   comments=[]):
          '''
          Construct a PlyElement from an array's metadata.
  
          len_types and val_types can be given as mappings from list
          property names to type strings (like 'u1', 'f4', etc., or
          'int8', 'float32', etc.). These can be used to define the length
          and value types of list properties.  List property lengths
          always default to type 'u1' (8-bit unsigned integer), and value
          types default to 'i4' (32-bit integer).
  
          '''
          if not isinstance(data, _np.ndarray):
              raise TypeError("only numpy arrays are supported")
  
          if len(data.shape) != 1:
              raise ValueError("only one-dimensional arrays are "
                               "supported")
  
          count = len(data)
  
          properties = []
          descr = data.dtype.descr
  
          for t in descr:
              if not isinstance(t[1], str):
                  raise ValueError("nested records not supported")
  
              if not t[0]:
                  raise ValueError("field with empty name")
  
              if len(t) != 2 or t[1][1] == 'O':
                  # non-scalar field, which corresponds to a list
                  # property in PLY.
  
                  if t[1][1] == 'O':
                      if len(t) != 2:
                          raise ValueError("non-scalar object fields not "
                                           "supported")
  
                  len_str = _data_type_reverse[len_types.get(t[0], 'u1')]
                  if t[1][1] == 'O':
                      val_type = val_types.get(t[0], 'i4')
                      val_str = _lookup_type(val_type)
                  else:
                      val_str = _lookup_type(t[1][1:])
  
                  prop = PlyListProperty(t[0], len_str, val_str)
              else:
                  val_str = _lookup_type(t[1][1:])
                  prop = PlyProperty(t[0], val_str)
  
              properties.append(prop)
  
          elt = PlyElement(name, properties, count, comments)
          elt.data = data
  
          return elt