26#if ! defined (octave_Sparse_h)
27#define octave_Sparse_h 1
29#include "octave-config.h"
44template <
typename T,
typename Alloc>
74 octave::refcount<octave_idx_type>
m_count;
77 :
Alloc (), m_data (T_allocate (1)), m_ridx (idx_type_allocate (1)),
78 m_cidx (idx_type_allocate (1)),
79 m_nzmax (1), m_nrows (0), m_ncols (0), m_count (1)
83 :
Alloc (), m_data (T_allocate (1)), m_ridx (idx_type_allocate (1)),
84 m_cidx (idx_type_allocate (n+1)),
85 m_nzmax (1), m_nrows (n), m_ncols (n), m_count (1)
89 :
Alloc (), m_data (T_allocate (nz > 0 ? nz : 1)),
90 m_ridx (idx_type_allocate (nz > 0 ? nz : 1)),
91 m_cidx (idx_type_allocate (nc+1)),
92 m_nzmax (nz > 0 ? nz : 1), m_nrows (nr), m_ncols (nc), m_count (1)
97 :
Alloc (), m_data (T_allocate (nz)),
98 m_ridx (idx_type_allocate (nz)),
99 m_cidx (idx_type_allocate (nc+1)),
100 m_nzmax (nz), m_nrows (nr), m_ncols (nc), m_count (1)
102 std::copy_n (
d, nz, m_data);
103 std::copy_n (r, nz, m_ridx);
104 std::copy_n (c, m_ncols + 1, m_cidx);
107 template <
typename U>
110 :
Alloc (), m_data (T_allocate (nz)),
111 m_ridx (idx_type_allocate (nz)),
112 m_cidx (idx_type_allocate (nc+1)),
113 m_nzmax (nz), m_nrows (nr), m_ncols (nc), m_count (1)
115 std::copy_n (
d, nz, m_data);
116 std::copy_n (r, nz, m_ridx);
117 std::copy_n (c, nc + 1, m_cidx);
120 template <
typename U>
124 :
Alloc (xallocator), m_data (
d), m_ridx (r), m_cidx (c),
125 m_nzmax (nz), m_nrows (dv(0)), m_ncols (dv(1)), m_count (1)
129 :
Alloc (), m_data (T_allocate (a.m_nzmax)),
130 m_ridx (idx_type_allocate (a.m_nzmax)),
131 m_cidx (idx_type_allocate (a.m_ncols + 1)),
132 m_nzmax (a.m_nzmax), m_nrows (a.m_nrows), m_ncols (a.m_ncols),
136 std::copy_n (a.
m_data, nz, m_data);
137 std::copy_n (a.
m_ridx, nz, m_ridx);
138 std::copy_n (a.
m_cidx, m_ncols + 1, m_cidx);
143 T_deallocate (m_data, m_nzmax);
144 idx_type_deallocate (m_ridx, m_nzmax);
145 idx_type_deallocate (m_cidx, m_ncols + 1);
171 OCTAVE_API void maybe_compress (
bool remove_zeros);
182 template <
typename U,
typename A>
friend class Sparse;
190 typename T_Alloc_traits::allocator_type& alloc = *
this;
193 for (
size_t i = 0; i <
len; i++)
194 T_Alloc_traits::construct (alloc, data+i);
201 typename T_Alloc_traits::allocator_type& alloc = *
this;
203 for (
size_t i = 0; i <
len; i++)
204 T_Alloc_traits::destroy (alloc, data+i);
205 T_Alloc_traits::deallocate (alloc, data,
len);
210 typename idx_type_Alloc_traits::allocator_type alloc = *
this;
213 for (
size_t i = 0; i <
len; i++)
214 idx_type_Alloc_traits::construct (alloc, idx+i);
221 typename idx_type_Alloc_traits::allocator_type alloc = *
this;
223 for (
size_t i = 0; i <
len; i++)
224 idx_type_Alloc_traits::destroy (alloc, idx+i);
225 idx_type_Alloc_traits::deallocate (alloc, idx,
len);
233 if (m_rep->m_count > 1)
237 if (--m_rep->m_count == 0)
257 : m_rep (nil_rep ()), m_dimensions (
dim_vector (0, 0))
274 m_dimensions (dv) { }
299 template <
typename U>
302 a.nzmax (), a.data (),
303 a.ridx (), a.cidx ())),
304 m_dimensions (a.dims ()) { }
308 : m_rep (a.m_rep), m_dimensions (a.m_dimensions)
320 Sparse (
const Array<T>& a,
const octave::idx_vector& r,
const octave::idx_vector& c,
356 while (cidx (ret+1) < k)
363 return (
static_cast<std::size_t
> (cols () + 1) *
sizeof (
octave_idx_type)
364 +
static_cast<std::size_t
> (nzmax ())
409 return m_rep->
celem (i, j);
423 if (n < 0 || n >=
numel ())
424 range_error (
"T& Sparse<T>::checkelem", n);
434 if (i < 0 || j < 0 || i >= dim1 () || j >= dim2 ())
435 range_error (
"T& Sparse<T>::checkelem", i, j);
448 range_error (
"T& Sparse<T>::checkelem",
ra_idx);
485 if (n < 0 || n >=
numel ())
486 range_error (
"T Sparse<T>::checkelem", n);
493 if (i < 0 || j < 0 || i >= dim1 () || j >= dim2 ())
494 range_error (
"T Sparse<T>::checkelem", i, j);
504 range_error (
"T Sparse<T>::checkelem",
ra_idx);
544 return permute (vec,
true);
565 bool issquare ()
const {
return (dim1 () == dim2 ()); }
567 bool isempty ()
const {
return (rows () < 1 || cols () < 1); }
583 make_unique ();
return m_rep->
ridx (i);
596 make_unique ();
return m_rep->
cidx (i);
608 OCTAVE_API void delete_elements (
const octave::idx_vector& i);
610 OCTAVE_API void delete_elements (
int dim,
const octave::idx_vector& i);
612 OCTAVE_API void delete_elements (
const octave::idx_vector& i,
const octave::idx_vector& j);
615 index (
const octave::idx_vector& i,
bool resize_ok =
false)
const;
618 index (
const octave::idx_vector& i,
const octave::idx_vector& j,
619 bool resize_ok =
false)
const;
621 OCTAVE_API void assign (
const octave::idx_vector& i,
624 OCTAVE_API void assign (
const octave::idx_vector& i,
const T& rhs);
627 assign (
const octave::idx_vector& i,
const octave::idx_vector& j,
631 assign (
const octave::idx_vector& i,
const octave::idx_vector& j,
635 print_info (std::ostream& os,
const std::string& prefix)
const;
652 template <
typename F,
bool zero>
655 return octave::any_all_test<F, T, zero> (fcn, data (), nnz ());
659 template <
typename F>
661 {
return test<F, false> (fcn); }
663 template <
typename F>
665 {
return test<F, true> (fcn); }
669 {
return test<bool (&) (T), false> (fcn); }
672 {
return test<bool (&) (const T&), false> (fcn); }
675 {
return test<bool (&) (T), true> (fcn); }
678 {
return test<bool (&) (const T&), true> (fcn); }
680 template <
typename U,
typename F>
685 U f_zero = fcn (0.0);
699 result.
data (ridx (i) + j * nr) = fcn (data (i));
712 result.
cidx (ii) = 0;
718 U val = fcn (data (i));
721 result.
data (ii) = val;
722 result.
ridx (ii++) = ridx (i);
726 result.
cidx (j+1) = ii;
736 template <
typename U>
739 {
return map<U, U (&) (T)> (fcn); }
741 template <
typename U>
743 map (U (&fcn) (
const T&))
const
744 {
return map<U, U (&) (const T&)> (fcn); }
756 T (*read_fcn) (std::istream&));
octave_idx_type compute_index(octave_idx_type n, const dim_vector &dims)
std::istream & read_sparse_matrix(std::istream &is, Sparse< T > &a, T(*read_fcn)(std::istream &))
N Dimensional Array with copy-on-write semantics.
SparseRep(const dim_vector &dv, octave_idx_type nz, U *d, octave_idx_type *r, octave_idx_type *c, const Alloc &xallocator=Alloc())
octave_idx_type cols() const
bool any_element_is_nan() const
void change_length(octave_idx_type nz)
octave_idx_type nzmax() const
octave_idx_type nnz() const
void T_deallocate(T_pointer data, size_t len)
octave::refcount< octave_idx_type > m_count
Alloc_traits::template rebind_traits< T > T_Alloc_traits
SparseRep(octave_idx_type n)
SparseRep(octave_idx_type nr, octave_idx_type nc, octave_idx_type nz, const T *d, const octave_idx_type *r, const octave_idx_type *c)
octave_idx_type columns() const
octave_idx_type rows() const
T cdata(octave_idx_type i) const
T_pointer T_allocate(size_t len)
SparseRep(const SparseRep &a)
T & data(octave_idx_type i)
void maybe_compress(bool remove_zeros)
octave_idx_type & ridx(octave_idx_type i)
SparseRep(octave_idx_type nr, octave_idx_type nc, octave_idx_type nz=1)
octave_idx_type length() const
SparseRep(octave_idx_type nr, octave_idx_type nc, octave_idx_type nz, const U *d, const octave_idx_type *r, const octave_idx_type *c)
T & elem(octave_idx_type r, octave_idx_type c)
T_Alloc_traits::pointer T_pointer
idx_type_pointer idx_type_allocate(size_t len)
std::allocator_traits< Alloc > Alloc_traits
octave_idx_type cridx(octave_idx_type i) const
idx_type_Alloc_traits::pointer idx_type_pointer
octave_idx_type & cidx(octave_idx_type i)
octave_idx_type ccidx(octave_idx_type i) const
Alloc_traits::template rebind_traits< octave_idx_type > idx_type_Alloc_traits
T celem(octave_idx_type r, octave_idx_type c) const
void idx_type_deallocate(idx_type_pointer idx, size_t len)
T & data(octave_idx_type i)
octave_idx_type cols() const
Sparse< U > map(U(&fcn)(const T &)) const
T xelem(const Array< octave_idx_type > &ra_idx) const
Sparse(octave_idx_type nr, octave_idx_type nc, octave_idx_type nz)
bool test_all(F fcn) const
octave_idx_type * ridx() const
octave_idx_type nzmax() const
Amount of storage for nonzero elements.
T checkelem(octave_idx_type n) const
Sparse(const dim_vector &dv, octave_idx_type nz)
T elem(const Array< octave_idx_type > &ra_idx) const
octave_idx_type get_col_index(octave_idx_type k)
octave_idx_type & ridx(octave_idx_type i)
octave_idx_type columns() const
bool test_any(bool(&fcn)(const T &)) const
T xelem(octave_idx_type n) const
T & xelem(octave_idx_type i, octave_idx_type j)
T & elem(octave_idx_type i, octave_idx_type j)
bool test_any(bool(&fcn)(T)) const
Sparse< T, Alloc > squeeze() const
T & checkelem(octave_idx_type n)
Sparse(octave_idx_type n)
octave_idx_type * cidx() const
octave_idx_type get_row_index(octave_idx_type k)
Sparse< U > map(F fcn) const
bool test_any(F fcn) const
T checkelem(const Array< octave_idx_type > &ra_idx) const
T & elem(octave_idx_type n)
octave_idx_type ridx(octave_idx_type i) const
octave_idx_type & xridx(octave_idx_type i)
octave_idx_type ndims() const
T elem(octave_idx_type n) const
T & checkelem(const Array< octave_idx_type > &ra_idx)
bool test_all(bool(&fcn)(T)) const
Sparse(const Sparse< U > &a)
octave_idx_type numel() const
T & elem(const Array< octave_idx_type > &ra_idx)
Sparse< T, Alloc > ipermute(const Array< octave_idx_type > &vec) const
T data(octave_idx_type i) const
bool test_all(bool(&fcn)(const T &)) const
Sparse(const dim_vector &dv, octave_idx_type nz, T *ptr, octave_idx_type *ridx, octave_idx_type *cidx, const Alloc &xallocator=Alloc())
T & xdata(octave_idx_type i)
T xelem(octave_idx_type i, octave_idx_type j) const
Sparse< T, Alloc > maybe_compress(bool remove_zeros=false)
std::size_t byte_size() const
octave_idx_type dim2() const
octave_idx_type dim1() const
T elem(octave_idx_type i, octave_idx_type j) const
octave_idx_type nnz() const
Actual number of nonzero terms.
Sparse(const Sparse< T, Alloc > &a)
T checkelem(octave_idx_type i, octave_idx_type j) const
octave_idx_type rows() const
T & xelem(const Array< octave_idx_type > &ra_idx)
void change_capacity(octave_idx_type nz)
Sparse(octave_idx_type nr, octave_idx_type nc)
T & checkelem(octave_idx_type i, octave_idx_type j)
Sparse< U > map(U(&fcn)(T)) const
T & xelem(octave_idx_type n)
octave_idx_type cidx(octave_idx_type i) const
Sparse< T, Alloc >::SparseRep * m_rep
bool any_element_is_nan() const
octave_idx_type & cidx(octave_idx_type i)
octave_idx_type & xcidx(octave_idx_type i)
octave_idx_type * xcidx()
octave_idx_type * xridx()
Vector representing the dimensions (size) of an Array.
octave_idx_type safe_numel() const
The following function will throw a std::bad_alloc () exception if the requested size is larger than ...
octave_idx_type ndims() const
Number of dimensions.
F77_RET_T const F77_DBLE const F77_DBLE F77_DBLE * d
T::size_type numel(const T &str)
const octave_base_value const Array< octave_idx_type > & ra_idx