def __init__(self, shape, dtype): """Initialize a new instance. Parameters ---------- shape : nonnegative int or sequence of nonnegative ints Number of entries of type ``dtype`` per axis in this space. A single integer results in a space with rank 1, i.e., 1 axis. dtype : Data type of elements in this space. Can be provided in any way the `numpy.dtype` constructor understands, e.g. as built-in type or as a string. For a data type with a ``dtype.shape``, these extra dimensions are added *to the left* of ``shape``. """ # Handle shape and dtype, taking care also of dtypes with shape try: shape, shape_in = tuple(safe_int_conv(s) for s in shape), shape except TypeError: shape, shape_in = (safe_int_conv(shape), ), shape if any(s < 0 for s in shape): raise ValueError('`shape` must have only nonnegative entries, got ' '{}'.format(shape_in)) dtype = np.dtype(dtype) # We choose this order in contrast to Numpy, since we usually want # to represent discretizations of vector- or tensor-valued functions, # i.e., if dtype.shape == (3,) we expect f[0] to have shape `shape`. self.__shape = dtype.shape + shape self.__dtype = dtype.base if is_real_dtype(self.dtype): # real includes non-floating-point like integers field = RealNumbers() self.__real_dtype = self.dtype self.__real_space = self self.__complex_dtype = TYPE_MAP_R2C.get(self.dtype, None) self.__complex_space = None # Set in first call of astype elif is_complex_floating_dtype(self.dtype): field = ComplexNumbers() self.__real_dtype = TYPE_MAP_C2R[self.dtype] self.__real_space = None # Set in first call of astype self.__complex_dtype = self.dtype self.__complex_space = self else: field = None LinearSpace.__init__(self, field)
def insert(self, index, other): """Return a copy with ``other`` inserted before ``index``. The given grid (``m`` dimensions) is inserted into the current one (``n`` dimensions) before the given index, resulting in a new `RectGrid` with ``n + m`` dimensions. Note that no changes are made in-place. Parameters ---------- index : int The index of the dimension before which ``other`` is to be inserted. Negative indices count backwards from ``self.ndim``. other : `RectGrid` The grid to be inserted Returns ------- newgrid : `RectGrid` The enlarged grid Examples -------- >>> g1 = RectGrid([0, 1], [-1, 0, 2]) >>> g2 = RectGrid([1], [-6, 15]) >>> g1.insert(1, g2) RectGrid( [0.0, 1.0], [1.0], [-6.0, 15.0], [-1.0, 0.0, 2.0] ) See Also -------- append """ if not isinstance(other, RectGrid): raise TypeError('`other` must be a `RectGrid` instance, got {}' ''.format(other)) idx = safe_int_conv(index) # Support backward indexing if idx < 0: idx = self.ndim + idx if not 0 <= idx <= self.ndim: raise IndexError('index {} outside the valid range 0 ... {}' ''.format(idx, self.ndim)) new_vecs = (self.coord_vectors[:idx] + other.coord_vectors + self.coord_vectors[idx:]) return RectGrid(*new_vecs)
def insert(self, index, *grids): """Return a copy with ``grids`` inserted before ``index``. The given grids are inserted (as a block) into ``self``, yielding a new grid whose number of dimensions is the sum of the numbers of dimensions of all involved grids. Note that no changes are made in-place. Parameters ---------- index : int The index of the dimension before which ``grids`` are to be inserted. Negative indices count backwards from ``self.ndim``. grid1, ..., gridN : `RectGrid` The grids to be inserted into ``self``. Returns ------- newgrid : `RectGrid` The enlarged grid. Examples -------- >>> g1 = RectGrid([0, 1], [-1, 0, 2]) >>> g2 = RectGrid([1], [-6, 15]) >>> g1.insert(1, g2) RectGrid( [ 0., 1.], [ 1.], [ -6., 15.], [-1., 0., 2.] ) >>> g1.insert(1, g2, g2) RectGrid( [ 0., 1.], [ 1.], [ -6., 15.], [ 1.], [ -6., 15.], [-1., 0., 2.] ) See Also -------- append """ index, index_in = safe_int_conv(index), index if not -self.ndim <= index <= self.ndim: raise IndexError('index {0} outside the valid range -{1} ... {1}' ''.format(index_in, self.ndim)) if index < 0: index += self.ndim if len(grids) == 0: # Copy of `self` return RectGrid(*self.coord_vectors) elif len(grids) == 1: # Insert single grid grid = grids[0] if not isinstance(grid, RectGrid): raise TypeError('{!r} is not a `RectGrid` instance' ''.format(grid)) new_vecs = (self.coord_vectors[:index] + grid.coord_vectors + self.coord_vectors[index:]) return RectGrid(*new_vecs) else: # Recursively insert first grid and the remaining into the result return self.insert(index, grids[0]).insert( index + grids[0].ndim, *(grids[1:]))
def insert(self, index, *intvs): """Return a copy with ``intvs`` inserted before ``index``. The given interval products are inserted (as a block) into ``self``, yielding a new interval product whose number of dimensions is the sum of the numbers of dimensions of all involved interval products. Note that no changes are made in-place. Parameters ---------- index : int Index of the dimension before which ``other`` is to be inserted. Must fulfill ``-ndim <= index <= ndim``. Negative indices count backwards from ``self.ndim``. intv1, ..., intvN : `IntervalProd` Interval products to be inserted into ``self``. Returns ------- newintvp : `IntervalProd` The enlarged interval product. Examples -------- >>> intv = IntervalProd([-1, 2], [-0.5, 3]) >>> intv2 = IntervalProd(0, 1) >>> intv.insert(0, intv2) IntervalProd([0.0, -1.0, 2.0], [1.0, -0.5, 3.0]) >>> intv.insert(-1, intv2) IntervalProd([-1.0, 0.0, 2.0], [-0.5, 1.0, 3.0]) >>> intv.insert(1, intv2, intv2) IntervalProd([-1.0, 0.0, 0.0, 2.0], [-0.5, 1.0, 1.0, 3.0]) """ index, index_in = safe_int_conv(index), index if not -self.ndim <= index <= self.ndim: raise IndexError('index {0} outside the valid range -{1} ... {1}' ''.format(index_in, self.ndim)) if index < 0: index += self.ndim if len(intvs) > 1: return self.insert(index, intvs[0]).insert(index + intvs[0].ndim, *(intvs[1:])) else: intv = intvs[0] if not isinstance(intv, IntervalProd): raise TypeError('{!r} is not a `IntervalProd` instance' ''.format(intv)) new_min_pt = np.empty(self.ndim + intv.ndim) new_max_pt = np.empty(self.ndim + intv.ndim) new_min_pt[:index] = self.min_pt[:index] new_max_pt[:index] = self.max_pt[:index] new_min_pt[index:index + intv.ndim] = intv.min_pt new_max_pt[index:index + intv.ndim] = intv.max_pt if index < self.ndim: # Avoid IndexError new_min_pt[index + intv.ndim:] = self.min_pt[index:] new_max_pt[index + intv.ndim:] = self.max_pt[index:] return IntervalProd(new_min_pt, new_max_pt)