Exemple #1
0
 def _add_prop_or_const(self, name, carray):
     """Add a new property or constant given the name and carray, note
     that this assumes that this property is already added to the
     particle array.
     """
     np_array = self._get_array(carray)
     g_ary = Array(np_array.dtype, n=carray.length, backend=self.backend)
     g_ary.set(np_array)
     self._data[name] = g_ary
     setattr(self, name, g_ary)
Exemple #2
0
    def _remove_particles_bool(self, if_remove):
        """ Remove particle i if if_remove[i] is True
        """
        num_indices = int(array.sum(if_remove, backend=self.backend))

        if num_indices == 0:
            return

        num_particles = self.get_number_of_particles()
        new_indices = Array(np.uint32,
                            n=(num_particles - num_indices),
                            backend=self.backend)
        num_removed_particles = array.empty(1,
                                            dtype=np.int32,
                                            backend=self.backend)

        remove_knl, stride_knl = self._get_remove_particles_bool_kernels()

        remove_knl(if_remove=if_remove,
                   new_indices=new_indices,
                   num_removed_particles=num_removed_particles,
                   num_particles=num_particles)

        new_num_particles = num_particles - int(num_removed_particles.get())

        strides = set(self._particle_array.stride.values())
        s_indices = {1: new_indices}
        for stride in strides:
            if stride == 1:
                continue
            size = new_num_particles * stride
            s_index = Array(np.uint32, n=size, backend=self.backend)
            stride_knl(new_indices, s_index, size, stride)
            s_indices[stride] = s_index

        for prop in self.properties:
            stride = self._particle_array.stride.get(prop, 1)
            s_index = s_indices[stride]
            self._data[prop].align(s_index)
            setattr(self, prop, self._data[prop])

        self.align_particles()
Exemple #3
0
def test_align(backend):
    check_import(backend)

    # Given
    dev_array = Array(np.int32, backend=backend)
    orig_array = array.arange(0, 16, 1, dtype=np.int32, backend=backend)
    dev_array.set_data(orig_array)
    indices = array.arange(15, -1, -1, dtype=np.int32, backend=backend)

    # When
    dev_array.align(indices)

    # Then
    assert np.all(dev_array.get() == indices.get())
Exemple #4
0
def test_remove(backend):
    check_import(backend)

    # Given
    dev_array = Array(np.int32, backend=backend)
    orig_array = array.arange(0, 16, 1, dtype=np.int32, backend=backend)
    dev_array.set_data(orig_array)
    indices = array.arange(0, 8, 1, dtype=np.int32, backend=backend)

    # When
    dev_array.remove(indices)

    # Then
    assert np.all(dev_array.get() == (8 + indices).get())
Exemple #5
0
    def append_parray(self, parray):
        """ Add particles from a particle array

        properties that are not there in self will be added
        """
        if parray.gpu is None:
            parray.set_device_helper(DeviceHelper(parray))

        if parray.gpu.get_number_of_particles() == 0:
            return

        num_extra_particles = parray.gpu.get_number_of_particles()
        old_num_particles = self.get_number_of_particles()
        new_num_particles = num_extra_particles + old_num_particles

        # extend current arrays by the required number of particles
        self.extend(num_extra_particles)

        my_stride = self._particle_array.stride
        for prop_name in parray.gpu.properties:
            stride = parray.stride.get(prop_name, 1)
            if stride > 1 and prop_name not in my_stride:
                my_stride[prop_name] = stride
            if prop_name in self.properties:
                arr = self._data[prop_name]
                source = parray.gpu.get_device_array(prop_name)
                arr.dev[old_num_particles * stride:] = source.dev
            else:
                # meaning this property is not there in self.
                dtype = parray.gpu.get_device_array(prop_name).dtype
                arr = Array(dtype,
                            n=new_num_particles * stride,
                            backend=self.backend)
                arr.fill(parray.default_values[prop_name])
                self.update_prop(prop_name, arr)

                # now add the values to the end of the created array
                dest = self._data[prop_name]
                source = parray.gpu.get_device_array(prop_name)
                dest.dev[old_num_particles * stride:] = source.dev

        for const in parray.gpu.constants:
            if const not in self.constants:
                arr = parray.gpu.get_device_array(const)
                self.update_const(const, arr.copy())

        if num_extra_particles > 0:
            self.align_particles()
Exemple #6
0
    def remove_particles(self, indices):
        """ Remove particles whose indices are given in index_list.

        We repeatedly interchange the values of the last element and
        values from the index_list and reduce the size of the array
        by one. This is done for every property that is being maintained.

        Parameters
        ----------

        indices : array
            an array of indices, this array can be a list, numpy array
            or a LongArray.

        Notes
        -----

        Pseudo-code for the implementation::

            if index_list.length > number of particles
                raise ValueError

            sorted_indices <- index_list sorted in ascending order.

            for every every array in property_array
                array.remove(sorted_indices)

        """
        if len(indices) > self.get_number_of_particles():
            msg = 'Number of particles to be removed is greater than'
            msg += 'number of particles in array'
            raise ValueError(msg)

        num_particles = self.get_number_of_particles()
        if_remove = Array(np.int32, n=num_particles, backend=self.backend)
        if_remove.fill(0)

        fill_if_remove_knl = self._get_remove_particles_kernel()
        fill_if_remove_knl(indices, if_remove, num_particles)

        self._remove_particles_bool(if_remove)
Exemple #7
0
def make_dev_array(backend, n=16):
    dev_array = Array(np.int32, n=n, backend=backend)
    dev_array.fill(0)
    dev_array[0] = 1
    return dev_array