SparseArray#

class numpy::SparseArray#

numpy C++ class.

Example#

#include <numpy/np_ndarray.h>
using namespace numpy;

// Use SparseArray
SparseArray obj;
// ... operations ...

Constructors#

Signature

Location

Example

SparseArray(const numpy::NDArray<T>& dense, T fill_value)

df_sparse_array.h:79

explicit SparseArray(const numpy::NDArray<T>& dense)

df_sparse_array.h:92

SparseArray(const numpy::NDArray<T>& sp_values, const numpy::NDArray<numpy::int64>& sp_index, T fill_value, size_t length)

df_sparse_array.h:108

SparseArray(const std::vector<T>& values, T fill_value)

df_sparse_array.h:123

Construction#

Signature

Return Type

Location

Example

static SparseArray<T> from_dense(const numpy::NDArray<T>& dense, T fill_value)

static SparseArray<T>

df_sparse_array.h:806

View

static SparseArray<T> from_dense(const numpy::NDArray<T>& dense)

static SparseArray<T>

df_sparse_array.h:813

View

Array Creation#

Signature

Return Type

Location

Example

bool empty() const

bool

df_sparse_array.h:186

View

Indexing / Selection#

Signature

Return Type

Location

Example

T at(size_t index) const

T

df_sparse_array.h:267

View

Statistics#

Signature

Return Type

Location

Example

std::optional<T> max() const

std::optional<T>

df_sparse_array.h:665

View

double mean() const

double

df_sparse_array.h:593

View

std::optional<T> min() const

std::optional<T>

df_sparse_array.h:628

View

std::optional<double> std(int ddof = 1) const

std::optional<double>

df_sparse_array.h:702

View

\* Optimized: sum(sp_values) + fill_count \* fill_value

* Optimized:

df_sparse_array.h:566

View

T sum() const

T

df_sparse_array.h:568

View

std::optional<double> var(int ddof = 1) const

std::optional<double>

df_sparse_array.h:711

View

Logical#

Signature

Return Type

Location

Example

bool all() const

bool

df_sparse_array.h:776

View

bool any() const

bool

df_sparse_array.h:750

View

I/O#

Signature

Return Type

Location

Example

numpy::NDArray<T> to_dense() const

numpy::NDArray<T>

df_sparse_array.h:296

View

std::string to_string() const

std::string

df_sparse_array.h:866

View

Type Handling#

Signature

Return Type

Location

Example

SparseArray<T> copy() const

SparseArray<T>

df_sparse_array.h:316

View

Type Checking#

Signature

Return Type

Location

Example

bool is_fill(size_t index) const

bool

df_sparse_array.h:274

bool is_fill_value(T val) const

bool

df_sparse_array.h:46

Other Methods#

Signature

Return Type

Location

Example

SparseArray<T> binary_op(const SparseArray<T>& other, Op op) const

SparseArray<T>

df_sparse_array.h:973

build_from_dense(dense)

df_sparse_array.h:85

build_from_dense(dense)

df_sparse_array.h:98

build_from_dense(dense)

df_sparse_array.h:133

void build_from_dense(const numpy::NDArray<T>& dense)

void

df_sparse_array.h:910

numpy::NDArray<numpy::bool\_> compare_op(const SparseArray<T>& other, Op op) const

numpy::NDArray<numpy::bool_>

df_sparse_array.h:1006

static SparseArray<T> concat(const std::vector<SparseArray<T>>& arrays)

static SparseArray<T>

df_sparse_array.h:820

size_t count() const

size_t

df_sparse_array.h:423

View

numpy::NDArray<T> dense(std::vector<size_t>

numpy::NDArray<T>

df_sparse_array.h:129

View

double density() const

double

df_sparse_array.h:233

dtype_type dtype() const

dtype_type

df_sparse_array.h:143

View

T fill_value() const

T

df_sparse_array.h:218

View

SparseArray<T> fillna(T value) const

SparseArray<T>

df_sparse_array.h:376

T find_value_at(size_t index) const

T

df_sparse_array.h:951

numpy::NDArray<numpy::bool\_> isna() const

numpy::NDArray<numpy::bool_>

df_sparse_array.h:332

size_t len() const

size_t

df_sparse_array.h:193

size_t nbytes() const

size_t

df_sparse_array.h:157

View

size_t nbytes_dense() const

size_t

df_sparse_array.h:165

constexpr int ndim() const

constexpr int

df_sparse_array.h:172

View

numpy::NDArray<numpy::int64> new_sp_index(std::vector<size_t>

numpy::NDArray<numpy::int64>

df_sparse_array.h:410

numpy::NDArray<T> new_sp_values(std::vector<size_t>

numpy::NDArray<T>

df_sparse_array.h:409

numpy::NDArray<numpy::bool\_> notna() const

numpy::NDArray<numpy::bool_>

df_sparse_array.h:363

size_t npoints() const

size_t

df_sparse_array.h:225

op(dense1.getElementAt(

df_sparse_array.h:985

op(fill_value\_, scalar), length\_)

df_sparse_array.h:1002

std::string repr() const

std::string

df_sparse_array.h:897

numpy::NDArray<T> result_dense(std::vector<size_t>

numpy::NDArray<T>

df_sparse_array.h:982

numpy::NDArray<numpy::bool\_> scalar_compare(T scalar, Op op) const

numpy::NDArray<numpy::bool_>

df_sparse_array.h:1023

SparseArray<T> scalar_op(T scalar, Op op) const

SparseArray<T>

df_sparse_array.h:994

std::vector<size_t> shape() const

std::vector<size_t>

df_sparse_array.h:179

View

size_t size() const

size_t

df_sparse_array.h:150

View

const numpy::NDArray<numpy::int64>& sp_index() const

const numpy::NDArray<numpy::int64>&

df_sparse_array.h:211

numpy::NDArray<numpy::int64> sp_index(std::vector<size_t>

numpy::NDArray<numpy::int64>

df_sparse_array.h:852

const numpy::NDArray<T>& sp_values() const

const numpy::NDArray<T>&

df_sparse_array.h:204

numpy::NDArray<T> sp_values(std::vector<size_t>

numpy::NDArray<T>

df_sparse_array.h:851

double sparsity() const

double

df_sparse_array.h:242

void validate_sparse_data()

void

df_sparse_array.h:931

Code Examples#

The following examples are extracted from the test suite.

from_dense (np_test_3_all.cpp:19939)
19929      std::cout << "========= CSR Matrix - basic functionality =======================";
19930
19931      numpy::NDArray<double> dense({ 4, 4 });
19932      dense.setElementAt({ 0, 0 }, 1.0);
19933      dense.setElementAt({ 0, 3 }, 2.0);
19934      dense.setElementAt({ 1, 1 }, 3.0);
19935      dense.setElementAt({ 2, 2 }, 4.0);
19936      dense.setElementAt({ 3, 0 }, 5.0);
19937      dense.setElementAt({ 3, 3 }, 6.0);
19938
19939      auto csr = numpy::sparse::CSRMatrix<double>::from_dense(dense);
19940
19941      if (csr.rows() != 4 || csr.cols() != 4 || csr.nnz() != 6) {
19942        std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : Incorrect matrix dimensions";
19943        throw std::runtime_error("np_test_sparse_csr_basic failed: dimension mismatch");
19944      }
19945
19946      if (!csr.check_format()) {
19947        std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : CSR format validation failed";
19948        throw std::runtime_error("np_test_sparse_csr_basic failed: invalid format");
19949      }
from_dense (np_test_3_all.cpp:19939)
19929      std::cout << "========= CSR Matrix - basic functionality =======================";
19930
19931      numpy::NDArray<double> dense({ 4, 4 });
19932      dense.setElementAt({ 0, 0 }, 1.0);
19933      dense.setElementAt({ 0, 3 }, 2.0);
19934      dense.setElementAt({ 1, 1 }, 3.0);
19935      dense.setElementAt({ 2, 2 }, 4.0);
19936      dense.setElementAt({ 3, 0 }, 5.0);
19937      dense.setElementAt({ 3, 3 }, 6.0);
19938
19939      auto csr = numpy::sparse::CSRMatrix<double>::from_dense(dense);
19940
19941      if (csr.rows() != 4 || csr.cols() != 4 || csr.nnz() != 6) {
19942        std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : Incorrect matrix dimensions";
19943        throw std::runtime_error("np_test_sparse_csr_basic failed: dimension mismatch");
19944      }
19945
19946      if (!csr.check_format()) {
19947        std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : CSR format validation failed";
19948        throw std::runtime_error("np_test_sparse_csr_basic failed: invalid format");
19949      }
empty (np_test_1_all.cpp:6316)
6306}
6307
6308void test_data_generator_emptyBenchmarkSorting() {
6309    std::cout << "========= test_data_generator_empty =======================";
6310
6311    DataGenerator<int> gen(42);
6312
6313    // Test empty data generation
6314    std::vector<int> data = gen.generate(0, DataPattern::RANDOM);
6315
6316    if (!(data.empty())) {
6317        std::string description = std::string("test_data_generator_emptyBenchmarkSorting():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(data.empty())";
6318        std::cout << std::string("[FAIL] ") + description << std::endl;
6319        throw std::runtime_error(description);
6320    }
6321
6322    // std::cout << "Empty data generation test passed" << std::endl;
6323
6324    std::cout << " -> tests passed" << std::endl;
6325}
at (np_test_1_all.cpp:144)
134    array.setElementAt({0, 0}, 1);
135    array.setElementAt({0, 1}, 2);
136    array.setElementAt({0, 2}, 3);
137    array.setElementAt({1, 1}, 5);
138    array.setElementAt({2, 2}, 9);
139
140    // std::cout << "Array after setting elements:" << std::endl;
141    //array.printArray();
142
143    // std::cout << "Element at (1,1): " << array.getElementAt({1, 1}) << std::endl;
144    // std::cout << "Element at (2,2): " << array.getElementAt({2, 2});
145
146    std::cout << " -> tests passed" << std::endl;
147}
148
149void testArithmetic() {
150    std::cout << "========= testArithmeticOperations =======================";
151
152    auto array1 = createFloat32Array({2, 2}, 5.0f);
153    auto array2 = createFloat32Array({2, 2}, 3.0f);
max (np_test_1_all.cpp:7274)
7264    if (sizeof(uintp) == sizeof(void*)) {
7265        // std::cout << "                -> uintp size matches pointer size";
7266    } else {
7267        // std::cout << "  ✗ uintp size doesn't match pointer size" << std::endl;
7268    }
7269
7270    // Test range limits
7271    // std::cout << "Range Information:" << std::endl;
7272    // std::cout << "  intp min: " << std::numeric_limits<intp>::min() << std::endl;
7273    // std::cout << "  intp max: " << std::numeric_limits<intp>::max() << std::endl;
7274    // std::cout << "  uintp max: " << std::numeric_limits<uintp>::max() << std::endl;
7275    // std::cout << "  longdouble digits: " << std::numeric_limits<longdouble>::digits << std::endl;
7276
7277    std::cout << " -> tests passed" << std::endl;
7278}
7279
7280void testComplexArithmeticExtendedTypes() {
7281    std::cout << "========= testComplexArithmeticExtendedTypes =======================";
7282
7283    clongdouble c1(3.0L, 4.0L);  // 3 + 4i
mean (np_test_1_all.cpp:11714)
11704    // Create test array
11705    auto array = createInt32Array({ 2, 3 }, 0);
11706    array.setElementAt({ 0, 0 }, 1);
11707    array.setElementAt({ 0, 1 }, 2);
11708    array.setElementAt({ 0, 2 }, 3);
11709    array.setElementAt({ 1, 0 }, 4);
11710    array.setElementAt({ 1, 1 }, 5);
11711    array.setElementAt({ 1, 2 }, 6);
11712
11713    // Test mean without axis
11714    auto mean_all = mean(array);
11715    if (!(approx_equal(mean_all.getElementAt({ 0 }), 3.5, 1e-10))) {
11716        std::string description = std::string("testBasicStatistics():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(approx_equal(mean_all.getElementAt({ 0 }), 3.5, 1e-10))";
11717        std::cout << std::string("[FAIL] ") + description << std::endl;
11718        throw std::runtime_error(description);
11719    }
11720    // std::cout << "[OK] mean (all elements) works correctly\n";
11721
11722    // Test mean along axis 0
11723    auto mean_axis0 = mean(array, 0);
11724    if (!(mean_axis0.getShape()[0] == 3)) {
min (np_test_1_all.cpp:2350)
2340        if (i % 3 == 0) {
2341            large_array.setElementAt({i}, object_(static_cast<int>(i)));
2342        } else if (i % 3 == 1) {
2343            large_array.setElementAt({i}, object_(static_cast<double>(i) * 0.5));
2344        } else {
2345            large_array.setElementAt({i}, object_(std::string("str") + std::to_string(i)));
2346        }
2347    }
2348
2349    // Verify pattern
2350    for (size_t i = 0; i < std::min(large_size, size_t(100)); ++i) {  // Check first 100
2351        object_ obj = large_array.getElementAt({i});
2352        if (i % 3 == 0) {
2353            if (!(obj.is_type<int>())) {
2354                std::string description = std::string("testArrayEdgeCases():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(obj.is_type<int>())";
2355                std::cout << std::string("[FAIL] ") + description << std::endl;
2356                throw std::runtime_error(description);
2357            }
2358        } else if (i % 3 == 1) {
2359            if (!(obj.is_type<double>())) {
2360                std::string description = std::string("unknown_function():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(obj.is_type<double>())";
std (np_test_1_all.cpp:11836)
11826    auto var_sample = var(array, std::nullopt, 1);  // ddof=1 for sample variance
11827    double expected_sample_var = 1.25 * 4.0 / 3.0;  // Bessel's correction
11828    if (!(approx_equal(var_sample.getElementAt({ 0 }), expected_sample_var, 1e-10))) {
11829        std::string description = std::string("testVarianceAndStandardDeviation():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(approx_equal(var_sample.getElementAt({ 0 }), expected_sample_var, 1e-10))";
11830        std::cout << std::string("[FAIL] ") + description << std::endl;
11831        throw std::runtime_error(description);
11832    }
11833    // std::cout << "[OK] Sample variance works correctly\n";
11834
11835    // Test standard deviation
11836    auto std_result = numpy::std(array, std::nullopt, 0);
11837    if (!(approx_equal(std_result.getElementAt({ 0 }), std::sqrt(expected_var), 1e-10))) {
11838        std::string description = std::string("testVarianceAndStandardDeviation():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(approx_equal(std_result.getElementAt({ 0 }), std::sqrt(expected_var), 1e-10))";
11839        std::cout << std::string("[FAIL] ") + description << std::endl;
11840        throw std::runtime_error(description);
11841    }
11842    // std::cout << "[OK] Standard deviation works correctly\n";
11843
11844    // Test along axis
11845    auto array2d = createFloat64Array({ 2, 2 }, 0);
11846    array2d.setElementAt({ 0, 0 }, 1.0);
sum (np_test_1_all.cpp:11766)
11756        throw std::runtime_error(description);
11757    }
11758    if (!(approx_equal(mean_axis1.getElementAt({ 1 }), 5.0, 1e-10))) {
11759        std::string description = std::string("testBasicStatistics():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(approx_equal(mean_axis1.getElementAt({ 1 }), 5.0, 1e-10))";
11760        std::cout << std::string("[FAIL] ") + description << std::endl;
11761        throw std::runtime_error(description);
11762    }
11763    // std::cout << "[OK] mean along axis 1 works correctly\n";
11764
11765    // Test sum
11766    auto sum_all = sum(array);
11767    if (!(sum_all.getElementAt({ 0 }) == 21)) {
11768        std::string description = std::string("testBasicStatistics():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(sum_all.getElementAt({ 0 }) == 21)";
11769        std::cout << std::string("[FAIL] ") + description << std::endl;
11770        throw std::runtime_error(description);
11771    }
11772    // std::cout << "[OK] sum works correctly\n";
11773
11774    // Test min and max
11775    auto min_all = min(array);
11776    auto max_all = max(array);
sum (np_test_1_all.cpp:11766)
11756        throw std::runtime_error(description);
11757    }
11758    if (!(approx_equal(mean_axis1.getElementAt({ 1 }), 5.0, 1e-10))) {
11759        std::string description = std::string("testBasicStatistics():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(approx_equal(mean_axis1.getElementAt({ 1 }), 5.0, 1e-10))";
11760        std::cout << std::string("[FAIL] ") + description << std::endl;
11761        throw std::runtime_error(description);
11762    }
11763    // std::cout << "[OK] mean along axis 1 works correctly\n";
11764
11765    // Test sum
11766    auto sum_all = sum(array);
11767    if (!(sum_all.getElementAt({ 0 }) == 21)) {
11768        std::string description = std::string("testBasicStatistics():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(sum_all.getElementAt({ 0 }) == 21)";
11769        std::cout << std::string("[FAIL] ") + description << std::endl;
11770        throw std::runtime_error(description);
11771    }
11772    // std::cout << "[OK] sum works correctly\n";
11773
11774    // Test min and max
11775    auto min_all = min(array);
11776    auto max_all = max(array);
var (np_test_1_all.cpp:11816)
11806    std::cout << "========= testVarianceAndStandardDeviation =======================";
11807
11808    // Create test array with known variance
11809    auto array = createFloat64Array({ 4 }, 0);
11810    array.setElementAt({ 0 }, 1.0);
11811    array.setElementAt({ 1 }, 2.0);
11812    array.setElementAt({ 2 }, 3.0);
11813    array.setElementAt({ 3 }, 4.0);
11814
11815    // Test variance (population)
11816    auto var_result = var(array, std::nullopt, 0);  // ddof=0 for population variance
11817    double expected_var = 1.25;  // Known variance for [1,2,3,4]
11818    if (!(approx_equal(var_result.getElementAt({ 0 }), expected_var, 1e-10))) {
11819        std::string description = std::string("testVarianceAndStandardDeviation():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(approx_equal(var_result.getElementAt({ 0 }), expected_var, 1e-10))";
11820        std::cout << std::string("[FAIL] ") + description << std::endl;
11821        throw std::runtime_error(description);
11822    }
11823    // std::cout << "[OK] Population variance works correctly\n";
11824
11825    // Test variance (sample)
11826    auto var_sample = var(array, std::nullopt, 1);  // ddof=1 for sample variance
all (np_test_4_all.cpp:23928)
23918                        }
23919                    }
23920                }
23921
23922                auto result = numpy::einsum<numpy::float64>("ijk->ik", {A});
23923
23924                if (result.getShape()[0] != 2 || result.getShape()[1] != 2) {
23925                    throw std::runtime_error("einsum partial sum shape wrong");
23926                }
23927
23928                // Sum over j: 1+2+3 = 6 for all (i,k) positions
23929                if (std::abs(result.getElementAt({0, 0}) - 6.0) > 1e-10 ||
23930                    std::abs(result.getElementAt({1, 1}) - 6.0) > 1e-10) {
23931                    throw std::runtime_error("einsum partial sum values wrong");
23932                }
23933
23934                // std::cout << "  OK: Partial sum: 'ijk->ik'\n";
23935            }
23936
23937            // Test 5: Size-1 dimension handling
23938            {
any (np_test_2_all.cpp:16758)
16748    // ANY() TESTS - SCALAR RESULT
16749    // ============================================================================
16750
16751    void np_test_logic_any_scalar_all_false() {
16752      std::cout << "========= any: all false elements =======================";
16753
16754      // Create array with all false/zero elements
16755      std::vector<double> data = { 0.0, 0.0, 0.0 };
16756      numpy::NDArray<double> arr = numpy::createArrayFromVector<double>({ 3 }, data);
16757
16758      bool result = numpy::any(arr);
16759
16760      if (result != false) {
16761        std::cout << "  [FAIL] : in np_test_logic_any_scalar_all_false() : expected false for all-zero array";
16762        throw std::runtime_error("np_test_logic_any_scalar_all_false failed: expected false");
16763      }
16764
16765      std::cout << " -> tests passed" << std::endl;
16766    }
16767
16768    void np_test_logic_any_scalar_all_true() {
to_dense (np_test_3_all.cpp:19951)
19941      if (csr.rows() != 4 || csr.cols() != 4 || csr.nnz() != 6) {
19942        std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : Incorrect matrix dimensions";
19943        throw std::runtime_error("np_test_sparse_csr_basic failed: dimension mismatch");
19944      }
19945
19946      if (!csr.check_format()) {
19947        std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : CSR format validation failed";
19948        throw std::runtime_error("np_test_sparse_csr_basic failed: invalid format");
19949      }
19950
19951      auto reconstructed = csr.to_dense();
19952      for (size_t i = 0; i < 4; ++i) {
19953        for (size_t j = 0; j < 4; ++j) {
19954          if (std::abs(dense.getElementAt({ i, j }) - reconstructed.getElementAt({ i, j })) > 1e-12) {
19955            std::cout << "  [FAIL] : in np_test_sparse_csr_basic() : Roundtrip conversion mismatch";
19956            throw std::runtime_error("np_test_sparse_csr_basic failed");
19957          }
19958        }
19959      }
19960
19961      std::cout << " -> tests passed" << std::endl;
to_string (np_test_1_all.cpp:454)
444    // Modify through different views
445    view1.setElementAt({0, 0}, 100);
446    view2.setElementAt({2, 1}, 200);  // This is (1, 2) in original
447    view3.setElementAt({0, 0}, 300);  // This is (1, 1) in original
448
449    // std::cout << "After modifications through multiple views:" << std::endl;
450    //original.printArray();
451
452    // Verify all changes are reflected
453    if (!(original.getElementAt({0, 0}) == 100)) {
454        std::string description = std::string("testAdvancedViewLifecycle():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(original.getElementAt({0, 0}) == 100)";
455        std::cout << std::string("[FAIL] ") + description << std::endl;
456        throw std::runtime_error(description);
457    }
458    if (!(original.getElementAt({1, 2}) == 200)) {
459        std::string description = std::string("testAdvancedViewLifecycle():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(original.getElementAt({1, 2}) == 200)";
460        std::cout << std::string("[FAIL] ") + description << std::endl;
461        throw std::runtime_error(description);
462    }
463    if (!(original.getElementAt({1, 1}) == 300)) {
464        std::string description = std::string("testAdvancedViewLifecycle():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(original.getElementAt({1, 1}) == 300)";
copy (np_test_1_all.cpp:9812)
9802    //original.printArray();
9803
9804    // The modification should be at position (1,1) in original
9805    if (!(original.getElementAt({1, 1}) == 9999)) {
9806        std::string description = std::string("testSliceCopyVsViewMemoryOwnership():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(original.getElementAt({1, 1}) == 9999)";
9807        std::cout << std::string("[FAIL] ") + description << std::endl;
9808        throw std::runtime_error(description);
9809    }
9810    // std::cout << "[OK] Slice view shares memory with original";
9811
9812    // Test slice copy (should be independent)
9813    auto slice_copy = original.sliceArray({{2, 4}, {2, 4}});
9814    // std::cout << "Slice copy [2:4, 2:4]:";
9815    //slice_copy.printArray();
9816
9817    slice_copy.setElementAt({0, 0}, 7777);
9818
9819    // std::cout << "After modifying slice copy at (0,0):" << std::endl;
9820    // std::cout << "Original array:" << std::endl;
9821    //original.printArray();
9822    // std::cout << "Slice copy:" << std::endl;
count (np_test_1_all.cpp:3616)
3606    // Create larger arrays for performance testing
3607    auto large_arr = NDArray<double>::createOnes({100, 100});
3608    auto broadcast_arr = NDArray<double>::createOnes({1, 100});
3609
3610    // Time the operation (basic timing)
3611    auto start = std::chrono::high_resolution_clock::now();
3612    auto result = large_arr.addArrays(broadcast_arr);
3613    auto end = std::chrono::high_resolution_clock::now();
3614
3615    auto duration = std::chrono::duration_cast<std::chrono::microseconds>(end - start);
3616    // std::cout << "Large array broadcasting took " << duration.count() << " microseconds" << std::endl;
3617
3618    // Verify result shape
3619    if (!((result.getShape() == std::vector<size_t>{100, 100}))) {
3620        std::string description = std::string("test_broadcasting_performance():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !((result.getShape() == std::vector<size_t>{100, 100}))";
3621        std::cout << std::string("[FAIL] ") + description << std::endl;
3622        throw std::runtime_error(description);
3623    }
3624    if (!(result.getElementAt({50, 50}) == 2.0)) {
3625        std::string description = std::string("test_broadcasting_performance():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(result.getElementAt({50, 50}) == 2.0)";
3626        std::cout << std::string("[FAIL] ") + description << std::endl;
dense (np_test_3_all.cpp:19931)
19921  namespace numpy_tests_sparse {
19922
19923    // ============================================================================
19924    // CSR MATRIX TESTS
19925    // ============================================================================
19926
19927    void np_test_sparse_csr_basic() {
19928      std::cout << "========= CSR Matrix - basic functionality =======================";
19929
19930      numpy::NDArray<double> dense({ 4, 4 });
19931      dense.setElementAt({ 0, 0 }, 1.0);
19932      dense.setElementAt({ 0, 3 }, 2.0);
19933      dense.setElementAt({ 1, 1 }, 3.0);
19934      dense.setElementAt({ 2, 2 }, 4.0);
19935      dense.setElementAt({ 3, 0 }, 5.0);
19936      dense.setElementAt({ 3, 3 }, 6.0);
19937
19938      auto csr = numpy::sparse::CSRMatrix<double>::from_dense(dense);
19939
19940      if (csr.rows() != 4 || csr.cols() != 4 || csr.nnz() != 6) {
dtype (np_test_3_all.cpp:7942)
7932  if (info.max != expected_max) {
7933    std::cerr << "[FAIL] IInfo<uint64_t>::max mismatch";
7934    throw std::runtime_error("IInfo uint64 max test failed");
7935  }
7936  // std::cout << "[OK] IInfo<uint64_t>::max = " << info.max << std::endl;
7937
7938  std::cout << " -> tests passed" << std::endl;
7939}
7940
7941// ============================================================================
7942// dtype() Tests - DType descriptor creation
7943// ============================================================================
7944
7945void np_test_dtype_from_string_integers() {
7946  std::cout << "========= np_test_dtype_from_string_integers =======================";
7947
7948  // Test integer type strings
7949  if (dtype("int8") != DType::INT8) {
7950    std::cerr << "[FAIL] dtype(\"int8\") should return INT8";
7951    throw std::runtime_error("dtype string test failed");
7952  }
fill_value (np_test_4_all.cpp:20577)
20567        }
20568
20569        // std::cout << "OK: masked_all_like(NDArray) test passed" << std::endl;
20570    }
20571
20572    // Test with custom fill value
20573    {
20574        NDArray<int> data({2, 2});
20575        auto masked = ma::masked_all_like(data, 999);
20576
20577        if (!(masked.fill_value() == 999)) {
20578            std::string description = std::string("np_test_phase6_ma_masked_all_like():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(masked.fill_value() == 999)";
20579            std::cout << std::string("[FAIL] ") + description << std::endl;
20580            throw std::runtime_error(description);
20581        }
20582
20583        // All elements should have fill_value
20584        for (size_t i = 0; i < 2; ++i) {
20585            for (size_t j = 0; j < 2; ++j) {
20586                if (!(masked.data().getElementAt({i, j}) == 999)) {
20587                    std::string description = std::string("np_test_phase6_ma_masked_all_like():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(masked.data().getElementAt({i, j}) == 999)";
nbytes (np_test_2_all.cpp:3547)
3537      }
3538
3539      // Test itemsize
3540      if (!(itemsize(arr) == sizeof(double))) {
3541          std::string description = std::string("testArrayInfo():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(itemsize(arr) == sizeof(double))";
3542          std::cout << std::string("[FAIL] ") + description << std::endl;
3543          throw std::runtime_error(description);
3544      }
3545
3546      // Test nbytes
3547      if (!(nbytes(arr) == 24 * sizeof(double))) {
3548          std::string description = std::string("testArrayInfo():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(nbytes(arr) == 24 * sizeof(double))";
3549          std::cout << std::string("[FAIL] ") + description << std::endl;
3550          throw std::runtime_error(description);
3551      }
3552
3553      // Test flags
3554      auto flags_info = flags(arr);
3555      if (!(flags_info.owndata == true)) {
3556          std::string description = std::string("testArrayInfo():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(flags_info.owndata == true)";
3557          std::cout << std::string("[FAIL] ") + description << std::endl;
ndim (np_test_2_all.cpp:3526)
3516    void testArrayInfo() {
3517      std::cout << "Testing array information functions...\n";
3518
3519      // Test basic info functions
3520      auto arr = createFloat64Array({ 2, 3, 4 });
3521      for (size_t i = 0; i < arr.getSize(); ++i) {
3522        arr.setElementAt({ i / 12, (i / 4) % 3, i % 4 }, static_cast<double>(i));
3523      }
3524
3525      // Test ndim
3526      if (!(ndim(arr) == 3)) {
3527          std::string description = std::string("testArrayInfo():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(ndim(arr) == 3)";
3528          std::cout << std::string("[FAIL] ") + description << std::endl;
3529          throw std::runtime_error(description);
3530      }
3531
3532      // Test size
3533      if (!(size(arr) == 24)) {
3534          std::string description = std::string("testArrayInfo():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !(size(arr) == 24)";
3535          std::cout << std::string("[FAIL] ") + description << std::endl;
3536          throw std::runtime_error(description);
shape (np_test_1_all.cpp:3751)
3741    }
3742
3743    for (size_t j = 0; j < 3; ++j) {
3744        arr3.setElementAt({0, j}, static_cast<double>((j + 1) * 100));  // [100, 200, 300]
3745    }
3746
3747    // Broadcast all arrays together
3748    std::vector<NDArray<double>> arrays = {arr1, arr2, arr3};
3749    auto broadcasted = broadcast_arrays(arrays);
3750
3751    // All should have shape (2, 3)
3752    for (const auto& arr : broadcasted) {
3753        if (!((arr.getShape() == std::vector<size_t>{2, 3}))) {
3754            std::string description = std::string("test_broadcast_arrays():") + __FILE__ + ":" + std::to_string(__LINE__) + ": !((arr.getShape() == std::vector<size_t>{2, 3}))";
3755            std::cout << std::string("[FAIL] ") + description << std::endl;
3756            throw std::runtime_error(description);
3757        }
3758    }
3759
3760    // Check values
3761    if (!(broadcasted[0].getElementAt({0, 1}) == 2.0)) {
size (np_test_1_all.cpp:47)
37using namespace numpy;
38using namespace numpy::benchmark;
39using namespace numpy::char_;
40
41// Helper functions for array comparison tests
42namespace {
43    const double TOLERANCE = 1e-10;
44
45    bool allTrue(const NDArray<bool>& arr) {
46        std::vector<size_t> indices(arr.getShape().size(), 0);
47        do {
48            if (!arr.getElementAt(indices)) {
49                return false;
50            }
51        } while (incrementIndices(indices, arr.getShape()));
52        return true;
53    }
54
55    bool allFalse(const NDArray<bool>& arr) {
56        std::vector<size_t> indices(arr.getShape().size(), 0);