Mercurial > hg > octave-lojdl
changeset 10760:76079e505f9d
optimize cellfun with uniform struct output
author | Jaroslav Hajek <highegg@gmail.com> |
---|---|
date | Thu, 01 Jul 2010 08:51:14 +0200 |
parents | d9e57045b9e1 |
children | 12dfe91e9fab |
files | src/ChangeLog src/oct-map.cc src/oct-map.h src/ov-struct.cc src/ov-struct.h |
diffstat | 5 files changed, 124 insertions(+), 6 deletions(-) [+] |
line wrap: on
line diff
--- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,17 @@ +2010-07-01 Jaroslav Hajek <highegg@gmail.com> + + * oct-map.cc (octave_fields::equal_up_to_order (const octave_fields&, + octave_idx_type *)): New overload. + (octave_fields::equal_up_to_order (const octave_fields&, + Array<octave_idx_type>&)): Use it here. + (octave_map::fast_elem_insert, + octave_map::fast_elem_extract): New methods. + * oct-map.h: Update decls. + * ov-struct.cc (octave_struct::fast_elem_extract, + octave_struct::fast_elem_insert, + octave_scalar_struct::fast_elem_insert_self): New methods. + * ov-struct.h: Update decls. + 2010-06-28 Jaroslav Hajek <highegg@gmail.com> * data.cc (single_type_concat): Optimize all scalars case where
--- a/src/oct-map.cc +++ b/src/oct-map.cc @@ -108,21 +108,17 @@ bool octave_fields::equal_up_to_order (const octave_fields& other, - Array<octave_idx_type>& perm) const + octave_idx_type* perm) const { bool retval = true; octave_idx_type n = nfields (); - if (perm.length () != n) - perm.clear (1, n); - else - perm.make_unique (); // optimization iterator p = begin (), q = other.begin (); for (; p != end () && q != other.end (); p++, q++) { if (p->first == q->first) - perm.xelem(p->second) = q->second; + perm[p->second] = q->second; else { retval = false; @@ -135,6 +131,19 @@ return retval; } +bool +octave_fields::equal_up_to_order (const octave_fields& other, + Array<octave_idx_type>& perm) const +{ + bool retval = true; + + octave_idx_type n = nfields (); + if (perm.length () != n) + perm.clear (1, n); + + return equal_up_to_order (other, perm.fortran_vec ()); +} + string_vector octave_fields::fieldnames (void) const { @@ -382,6 +391,45 @@ return retval; } +octave_scalar_map +octave_map::fast_elem_extract (octave_idx_type n) const +{ + octave_scalar_map retval (xkeys); + + extract_scalar (retval, n); + + return retval; +} + +bool +octave_map::fast_elem_insert (octave_idx_type n, + const octave_scalar_map& rhs) +{ + bool retval = false; + + octave_idx_type nf = nfields (); + if (rhs.xkeys.is_same (xkeys)) + { + for (octave_idx_type i = 0; i < nf; i++) + xvals[i](n) = rhs.xvals[i]; + + retval = true; + } + else + { + OCTAVE_LOCAL_BUFFER (octave_idx_type, perm, nf); + if (xkeys.equal_up_to_order (rhs.xkeys, perm)) + { + for (octave_idx_type i = 0; i < nf; i++) + xvals[i](n) = rhs.xvals[perm[i]]; + + retval = true; + } + } + + return retval; +} + octave_map octave_map::squeeze (void) const {
--- a/src/oct-map.h +++ b/src/oct-map.h @@ -124,6 +124,9 @@ // returns a permutation needed to bring the fields of *other* // into the order of *this*. bool equal_up_to_order (const octave_fields& other, + octave_idx_type* perm) const; + + bool equal_up_to_order (const octave_fields& other, Array<octave_idx_type>& perm) const; bool is_same (const octave_fields& other) const @@ -432,6 +435,12 @@ octave_map concat (const octave_map& rb, const Array<octave_idx_type>& ra_idx); + // like checkelem, but no check. + octave_scalar_map fast_elem_extract (octave_idx_type n) const; + + // element assignment, no bounds check + bool fast_elem_insert (octave_idx_type n, const octave_scalar_map& rhs); + private: octave_fields xkeys;
--- a/src/ov-struct.cc +++ b/src/ov-struct.cc @@ -1074,6 +1074,33 @@ return retval; } +octave_value +octave_struct::fast_elem_extract (octave_idx_type n) const +{ + if (n < map.numel ()) + return map.checkelem (n); + else + return octave_value (); +} + +bool +octave_struct::fast_elem_insert (octave_idx_type n, + const octave_value& x) +{ + bool retval = false; + + if (n < map.numel ()) + { + // To avoid copying the scalar struct, it just stores a pointer to + // itself. + const octave_scalar_map *sm_ptr; + void *here = reinterpret_cast<void *>(&sm_ptr); + return (x.get_rep().fast_elem_insert_self (here, btyp_struct) + && map.fast_elem_insert (n, *sm_ptr)); + } + + return retval; +} DEFINE_OCTAVE_ALLOCATOR(octave_scalar_struct); DEFINE_OV_TYPEID_FUNCTIONS_AND_DATA(octave_scalar_struct, "scalar struct", "struct"); @@ -1682,6 +1709,18 @@ return new octave_struct (octave_map (map)); } +bool +octave_scalar_struct::fast_elem_insert_self (void *where, builtin_type_t btyp) const +{ + + if (btyp == btyp_struct) + { + *(reinterpret_cast<const octave_scalar_map **>(where)) = ↦ + return true; + } + else + return false; +} /* %!shared x %! x(1).a=1; x(2).a=2; x(1).b=3; x(2).b=3;
--- a/src/ov-struct.h +++ b/src/ov-struct.h @@ -153,6 +153,12 @@ mxArray *as_mxArray (void) const; + octave_value + fast_elem_extract (octave_idx_type n) const; + + bool + fast_elem_insert (octave_idx_type n, const octave_value& x); + protected: // The associative array used to manage the structure data. @@ -268,6 +274,8 @@ mxArray *as_mxArray (void) const; + bool fast_elem_insert_self (void *where, builtin_type_t btyp) const; + protected: // The associative array used to manage the structure data.