Most NumPy arrays have some restrictions. When these conditions are met, NumPy exploits these characteristics to make the array faster, more memory efficient, and more convenient to use than less restrictive data structures.
All elements of the array must be of the same type of data.
Once created, the total size of the array can’t change.
The shape must be “rectangular”, not “jagged”; e.g., each row of a two-dimensional array must have the same number of columns.
You're loading a CSV with pandas and converting a column to a NumPy array for math. The column has a few 'N/A' strings mixed in with numbers. What happens when you call .to_numpy() on that column, and how would you fix it?
A teammate writes np.array([1, 2, 3.5, 'four']). What dtype does the resulting array have, and why might that bite them later when they try arithmetic?
You're debugging a pipeline where a float64 array suddenly becomes object dtype after a merge operation. The downstream model training fails with a cryptic error. Walk me through how you'd trace where the dtype change happened and what the likely culprit is.
Your team is deciding between using a structured dtype (record array) vs. a 2D float array for a new feature store. The data has columns of different types (int IDs, float scores, string categories). What are the tradeoffs in memory, access patterns, and downstream ML compatibility?
A high-throughput inference service uses NumPy arrays passed between processes via shared memory. You're seeing occasional segfaults when consumers read arrays produced by writers. What memory layout or dtype alignment issues could cause this, and how would you enforce safe contracts?
You're designing a custom C extension that writes directly into a NumPy array's data buffer. The array might be non-contiguous (e.g., a slice with stride > 1). How do you handle strided access safely without copying, and what dtype restrictions must you validate?
Your org is migrating a legacy codebase from NumPy 1.x to 2.0, which tightens dtype promotion rules (e.g., uint8 + int8 no longer upcasts to int16). Hundreds of pipelines silently change behavior. How do you design a migration strategy that catches regressions without blocking feature work?
You're defining a company-wide array interchange protocol for teams using NumPy, PyTorch, JAX, and CuPy. The protocol must specify dtype canonicalization, memory layout guarantees, and ownership semantics for zero-copy handoffs. What are the key restrictions you'd codify, and how do you handle dtype extensions (e.g., bfloat16) that not all runtimes support?