larray.Array.apply

Array.apply(transform, *args, by=None, axes=None, dtype=None, ascending=True, **kwargs) Union[Array, bool, int, float, str, bytes, generic, Tuple[Array, ...]][source]

Apply a transformation function to array elements.

Parameters
transformfunction

Function to apply. This function will be called in turn with each element of the array as the first argument and must return an Array, scalar or tuple. If returning arrays the axes of those arrays must be the same for all calls to the function.

*args

Extra arguments to pass to the function.

bystr, int or Axis or tuple/list/AxisCollection of the them, optional

Axis or axes along which to iterate. The function will thus be called with arrays having all axes not mentioned. Defaults to None (all axes). Mutually exclusive with the axes argument.

axesstr, int or Axis or tuple/list/AxisCollection of the them, optional

Axis or axes the arrays passed to the function will have. Defaults to None (the function is given scalars). Mutually exclusive with the by argument.

dtypetype or list of types, optional

Output(s) data type(s). Defaults to None (inspect all output values to infer it automatically).

ascendingbool, optional

Whether to iterate the axes in ascending order (from start to end). Defaults to True.

**kwargs

Extra keyword arguments are passed to the function (as keyword arguments).

Returns
Array or scalar, or tuple of them

Axes will be the union of those in axis and those of values returned by the function.

Examples

First let us define a test array

>>> arr = Array([[0, 2, 1],
...              [3, 1, 5]], 'a=a0,a1;b=b0..b2')
>>> arr
a\b  b0  b1  b2
 a0   0   2   1
 a1   3   1   5

Here is a simple function we would like to apply to each element of the array. Note that this particular example should rather be written as: arr ** 2 as it is both more concise and much faster.

>>> def square(x):
...     return x ** 2
>>> arr.apply(square)
a\b  b0  b1  b2
 a0   0   4   1
 a1   9   1  25

Functions can also be applied along some axes:

>>> # this is equivalent to (but much slower than): arr.sum('a')
... arr.apply(sum, axes='a')
b  b0  b1  b2
    3   3   6
>>> # this is equivalent to (but much slower than): arr.sum_by('a')
... arr.apply(sum, by='a')
a  a0  a1
    3   9

Applying the function along some axes will return an array with the union of those axes and the axes of the returned values. For example, let us define a function which returns the k highest values of an array.

>>> def topk(a, k=2):
...     return a.sort_values(ascending=False).ignore_labels().i[:k]
>>> arr.apply(topk, by='a')
a\b*  0  1
  a0  2  1
  a1  5  3

Other arguments can be passed to the function:

>>> arr.apply(topk, 3, by='a')
a\b*  0  1  2
  a0  2  1  0
  a1  5  3  1

or by using keyword arguments:

>>> arr.apply(topk, by='a', k=3)
a\b*  0  1  2
  a0  2  1  0
  a1  5  3  1

If the function returns several values (as a tuple), the result will be a tuple of arrays. For example, let use define a function which decompose an array in its mean and the difference to that mean :

>>> def mean_decompose(a):
...     mean = a.mean()
...     return mean, a - mean
>>> mean_by_a, diff_to_mean = arr.apply(mean_decompose, by='a')
>>> mean_by_a
a   a0   a1
   1.0  3.0
>>> diff_to_mean
a\b    b0    b1   b2
 a0  -1.0   1.0  0.0
 a1   0.0  -2.0  2.0