On 03/04/2016 12:26 AM, Lachlan Andrew wrote:
On 4 March 2016 at 16:37, Daniel J Sebald<address@hidden> wrote:
assign memory even from the start--not a bad strategy. However, at that
point, the member pointers r and d are initialized as r(0) and d(0). And
2)
delete [] r;
Now, the first line of code is more questionable. Typically one isn't
supposed to delete a NULL pointer.
Good catch, but deleting NULL pointers is valid in all
standards-compliant compilers, and some people advocate that rather
than checking for NULL first. See the discussion at
http://stackoverflow.com/questions/4190703/is-it-safe-to-delete-a-null-pointer#4190737
Yes, appears to be fine.
It turns out that ::change_length() is accessed much more than I
thought. It is used in the header in inline function
Sparse::change_capacity (octave_idx_type nz), and that routine is used
at least a half dozen times in the source file.
Anyway, so the path that "speye(10)" follows through the instantiation
(Sparse::Sparse) is
else if (a_scalar)
{
[snip]
else
{
idx_vector rr = r;
idx_vector cc = c;
const octave_idx_type *rd = rr.raw ();
const octave_idx_type *cd = cc.raw ();
I did a deeper dive on the code in that path, and I too find it to be
fine in terms of indexing. It is a bit tricky to follow because the
array length is one longer than the number of nc, but I can't find any
place where an index (of index) might be one index out of bounds.
The one thing that has me a bit confused is this raw() function:
const octave_idx_type *
idx_vector::raw (void)
{
if (rep->idx_class () != class_vector)
*this = idx_vector (as_array (), extent (0));
idx_vector_rep * r = dynamic_cast<idx_vector_rep *> (rep);
assert (r != 0);
return r->get_data ();
}