MCPcopy Create free account
hub / github.com/numpy/numpy / PyArray_AssignArray

Function PyArray_AssignArray

numpy/core/src/multiarray/array_assign_array.c:294–473  ·  view source on GitHub ↗

* An array assignment function for copying arrays, broadcasting 'src' into * 'dst'. This function makes a temporary copy of 'src' if 'src' and * 'dst' overlap, to be able to handle views of the same data with * different strides. * * dst: The destination array. * src: The source array. * wheremask: If non-NULL, a boolean mask specifying where to copy. * casting: An exception is raised if t

Source from the content-addressed store, hash-verified

292 * Returns 0 on success, -1 on failure.
293 */
294NPY_NO_EXPORT int
295PyArray_AssignArray(PyArrayObject *dst, PyArrayObject *src,
296 PyArrayObject *wheremask,
297 NPY_CASTING casting)
298{
299 int copied_src = 0;
300
301 npy_intp src_strides[NPY_MAXDIMS];
302
303 /* Use array_assign_scalar if 'src' NDIM is 0 */
304 if (PyArray_NDIM(src) == 0) {
305 return PyArray_AssignRawScalar(
306 dst, PyArray_DESCR(src), PyArray_DATA(src),
307 wheremask, casting);
308 }
309
310 /*
311 * Performance fix for expressions like "a[1000:6000] += x". In this
312 * case, first an in-place add is done, followed by an assignment,
313 * equivalently expressed like this:
314 *
315 * tmp = a[1000:6000] # Calls array_subscript in mapping.c
316 * np.add(tmp, x, tmp)
317 * a[1000:6000] = tmp # Calls array_assign_subscript in mapping.c
318 *
319 * In the assignment the underlying data type, shape, strides, and
320 * data pointers are identical, but src != dst because they are separately
321 * generated slices. By detecting this and skipping the redundant
322 * copy of values to themselves, we potentially give a big speed boost.
323 *
324 * Note that we don't call EquivTypes, because usually the exact same
325 * dtype object will appear, and we don't want to slow things down
326 * with a complicated comparison. The comparisons are ordered to
327 * try and reject this with as little work as possible.
328 */
329 if (PyArray_DATA(src) == PyArray_DATA(dst) &&
330 PyArray_DESCR(src) == PyArray_DESCR(dst) &&
331 PyArray_NDIM(src) == PyArray_NDIM(dst) &&
332 PyArray_CompareLists(PyArray_DIMS(src),
333 PyArray_DIMS(dst),
334 PyArray_NDIM(src)) &&
335 PyArray_CompareLists(PyArray_STRIDES(src),
336 PyArray_STRIDES(dst),
337 PyArray_NDIM(src))) {
338 /*printf("Redundant copy operation detected\n");*/
339 return 0;
340 }
341
342 if (PyArray_FailUnlessWriteable(dst, "assignment destination") < 0) {
343 goto fail;
344 }
345
346 /* Check the casting rule */
347 if (!PyArray_CanCastTypeTo(PyArray_DESCR(src),
348 PyArray_DESCR(dst), casting)) {
349 npy_set_invalid_cast_error(
350 PyArray_DESCR(src), PyArray_DESCR(dst), casting, NPY_FALSE);
351 goto fail;

Callers 9

PyArray_CopyIntoFunction · 0.85
PyArray_MoveIntoFunction · 0.85
array_copytoFunction · 0.85
PyArray_NewCopyFunction · 0.85
PyArray_CopyObjectFunction · 0.85
__New_PyArray_StdFunction · 0.85
PyArray_RoundFunction · 0.85
PyArray_ConjugateFunction · 0.85

Calls 15

PyArray_NDIMFunction · 0.85
PyArray_AssignRawScalarFunction · 0.85
PyArray_DESCRFunction · 0.85
PyArray_DATAFunction · 0.85
PyArray_CompareListsFunction · 0.85
PyArray_DIMSFunction · 0.85
PyArray_STRIDESFunction · 0.85
PyArray_CanCastTypeToFunction · 0.85
arrays_overlapFunction · 0.85
PyArray_NewLikeArrayFunction · 0.85

Tested by

no test coverage detected