Skip to content

BUG: array's append should respect the type of the array you are appending to #22427

Open

Description

@albertvaka

Describe the issue:

Calling np.append on a float32 array will return a float64 array unless we append explicitly a float32.

It seems confusing (and a potential performance issue) that the entire array gets casted up just because I appended something.

I think the type of the original array should be preserved, or append be given an optional dtype argument like other methods have.

Reproduce the code example:

import numpy as np
a = np.array([1, 2], dtype=np.float32)
print(a.dtype) # prints float32
b = np.append(a, 42)
print(b.dtype) # prints float64

The workaround is to explicitly append a float32 by doing np.float32(42) first, but it's quite hard to find out this cast is happening in the first place.

NumPy/Python version information:

1.23.3 3.10.6 (main, Aug 30 2022, 04:58:14) [Clang 13.1.6 (clang-1316.0.21.2.5)]

Context for the issue:

  • Apple's mps only supports float32.
  • numpy defaults to float64 everywhere if you are not careful.
  • This causes a crash on Macs (eg: when using numpy arrays from pytorch), but it could be a hidden performance issue on other places because of the casts (which IMO would be worse than the crash).

Activity

  1. maidaly commented on Oct 12, 2022

    @maidaly

    I solved it by adding dtype parameter to the append function to make sure that the new copy array generated from the append has the wanted dtype ..... and here is the result.
    numpy-Screenshot 2022-10-12

  2. seberg commented on Oct 13, 2022

    @seberg
    Member

    Hmmm, adding a dtype kwarg does add a decent work-around. I do agree that in principle we should probably just use the arr dtype and it is unfortunate that this is not the case.

    Should we actually consider changing this, though? append is a very thin alias around concatenate after all. So if we added a FutureWarning, users could switch to concatenate if they want the old behavior.
    If they need to silence the warning and get the new behavior, they would have to cast manually unfortunately.
    np.insert does have the "expected" behavior of casting to the first array.

    EDIT: I am very much presuming that most users already get the first array's dtype in any case, so the FutureWarning shouldn't be ubiquitous.

  3. MatteoRaso commented on Oct 13, 2022

    @MatteoRaso
    Contributor

    I think the change is good. The append function is far more commonly used than the concatenate function, so it would be annoying for users to constantly get a bunch of warnings in their code.

  4. mattip commented on Oct 13, 2022

    @mattip
    Member

    The documentation for append does not mention concatenate. It makes sense to me to add a dtype and even a cast argument to append, and to change the documentation to mention append is a thin layer around concatenate. What would the proposed message of a FutureWarning be?

  5. seberg commented on Oct 13, 2022

    @seberg
    Member

    The warning would be something like:

    if result.dtype is not arr.dtype:  # or == ?
        warnings.warn(FutureWarning,
                "in the future append will always cast the values to be appended to "
                "dtype of the array preserving the dtype exactly.\n"
                "If you do not wish this behavior use concatenate of which append "
                "is a thin layer.  To get the future behavior cast the values or "
                "use concatenate with `dtype=arr.dtype`")
    
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions