@@ -53,7 +53,7 @@ static VALUE nm_each_stored_with_indices(VALUE nmatrix);
5353static VALUE nm_each_ordered_stored_with_indices (VALUE nmatrix );
5454static VALUE nm_map_stored (VALUE nmatrix );
5555
56- static SLICE * get_slice ( size_t dim , int argc , VALUE * arg , size_t * shape );
56+ static void init_slice_no_alloc ( SLICE * slice , size_t dim , int argc , VALUE * arg , size_t * shape );
5757static VALUE nm_xslice (int argc , VALUE * argv , void * (* slice_func )(const STORAGE * , SLICE * ), void (* delete_func )(NMATRIX * ), VALUE self );
5858static VALUE nm_mset (int argc , VALUE * argv , VALUE self );
5959static VALUE nm_mget (int argc , VALUE * argv , VALUE self );
@@ -398,28 +398,6 @@ void Init_nmatrix() {
398398// Ruby Methods //
399399//////////////////
400400
401-
402- /*
403- * Slice constructor.
404- */
405- static SLICE * alloc_slice (size_t dim ) {
406- SLICE * slice = NM_ALLOC (SLICE );
407- slice -> coords = NM_ALLOC_N (size_t , dim );
408- slice -> lengths = NM_ALLOC_N (size_t , dim );
409- return slice ;
410- }
411-
412-
413- /*
414- * Slice destructor.
415- */
416- static void free_slice (SLICE * slice ) {
417- NM_FREE (slice -> coords );
418- NM_FREE (slice -> lengths );
419- NM_FREE (slice );
420- }
421-
422-
423401/*
424402 * Allocator.
425403 */
@@ -1272,7 +1250,12 @@ static VALUE nm_init_new_version(int argc, VALUE* argv, VALUE self) {
12721250 tmp_shape [m ] = shape [m ];
12731251 }
12741252
1275- SLICE * slice = get_slice (dim , dim , slice_argv , shape );
1253+ SLICE slice_s ;
1254+ SLICE * slice = & slice_s ;
1255+ slice -> coords = NM_ALLOCA_N (size_t , dim );
1256+ slice -> lengths = NM_ALLOCA_N (size_t , dim );
1257+ init_slice_no_alloc (slice , dim , dim , slice_argv , shape );
1258+
12761259 // Create a temporary dense matrix and use it to do a slice assignment on self.
12771260 NMATRIX * tmp = nm_create (nm ::DENSE_STORE , (STORAGE * )nm_dense_storage_create (dtype , tmp_shape , dim , v , v_size ));
12781261 nm_register_nmatrix (tmp );
@@ -1282,8 +1265,6 @@ static VALUE nm_init_new_version(int argc, VALUE* argv, VALUE self) {
12821265 if (stype == nm ::YALE_STORE ) nm_yale_storage_set (self , slice , rb_tmp );
12831266 else nm_list_storage_set (self , slice , rb_tmp );
12841267
1285- free_slice (slice );
1286-
12871268 // We need to free v if it's not the same size as tmp -- because tmp will have made a copy instead.
12881269 //if (nm_storage_count_max_elements(tmp->storage) != v_size)
12891270 // NM_FREE(v);
@@ -2018,7 +1999,11 @@ static VALUE nm_mset(int argc, VALUE* argv, VALUE self) {
20181999 NM_CONSERVATIVE (nm_register_value (& self ));
20192000 NM_CONSERVATIVE (nm_register_values (argv , argc ));
20202001
2021- SLICE * slice = get_slice (dim , argc - 1 , argv , NM_STORAGE (self )-> shape );
2002+ SLICE slice_s ;
2003+ SLICE * slice = & slice_s ;
2004+ slice -> coords = NM_ALLOCA_N (size_t , dim );
2005+ slice -> lengths = NM_ALLOCA_N (size_t , dim );
2006+ init_slice_no_alloc (slice , dim , argc - 1 , argv , NM_STORAGE (self )-> shape );
20222007
20232008 static void (* ttable [nm ::NUM_STYPES ])(VALUE , SLICE * , VALUE ) = {
20242009 nm_dense_storage_set ,
@@ -2028,8 +2013,6 @@ static VALUE nm_mset(int argc, VALUE* argv, VALUE self) {
20282013
20292014 ttable [NM_STYPE (self )](self , slice , argv [argc - 1 ]);
20302015
2031- free_slice (slice );
2032-
20332016 to_return = argv [argc - 1 ];
20342017
20352018 NM_CONSERVATIVE (nm_unregister_value (& self ));
@@ -2259,7 +2242,12 @@ static VALUE nm_xslice(int argc, VALUE* argv, void* (*slice_func)(const STORAGE*
22592242
22602243 nm_register_value (& result );
22612244
2262- SLICE * slice = get_slice (NM_DIM (self ), argc , argv , s -> shape );
2245+ SLICE slice_s ;
2246+ SLICE * slice = & slice_s ;
2247+ size_t dim = NM_DIM (self );
2248+ slice -> coords = NM_ALLOCA_N (size_t , dim );
2249+ slice -> lengths = NM_ALLOCA_N (size_t , dim );
2250+ init_slice_no_alloc (slice , dim , argc , argv , s -> shape );
22632251
22642252 if (slice -> single ) {
22652253 static void * (* ttable [nm ::NUM_STYPES ])(const STORAGE * , SLICE * ) = {
@@ -2280,8 +2268,6 @@ static VALUE nm_xslice(int argc, VALUE* argv, void* (*slice_func)(const STORAGE*
22802268 result = Data_Wrap_Struct (CLASS_OF (self ), nm_mark , delete_func , mat );
22812269 nm_unregister_nmatrix (mat );
22822270 }
2283-
2284- free_slice (slice );
22852271 }
22862272
22872273 nm_unregister_value (& result );
@@ -2623,19 +2609,17 @@ nm::dtype_t nm_dtype_guess(VALUE v) {
26232609 }
26242610}
26252611
2626-
2627-
26282612/*
2629- * Allocate and return a SLICE object, which will contain the appropriate coordinate and length information for
2630- * accessing some part of a matrix.
2613+ * Modify an existing SLICE object (with properly allocated memory),
2614+ * so that it will contain the appropriate coordinate and length information
2615+ * for accessing some part of a matrix.
26312616 */
2632- static SLICE * get_slice ( size_t dim , int argc , VALUE * arg , size_t * shape ) {
2617+ static void init_slice_no_alloc ( SLICE * slice , size_t dim , int argc , VALUE * arg , size_t * shape ) {
26332618 NM_CONSERVATIVE (nm_register_values (arg , argc ));
26342619
26352620 VALUE beg , end ;
26362621 int excl ;
26372622
2638- SLICE * slice = alloc_slice (dim );
26392623 slice -> single = true;
26402624
26412625 // r is the shape position; t is the slice position. They may differ when we're dealing with a
@@ -2693,7 +2677,6 @@ static SLICE* get_slice(size_t dim, int argc, VALUE* arg, size_t* shape) {
26932677 }
26942678
26952679 NM_CONSERVATIVE (nm_unregister_values (arg , argc ));
2696- return slice ;
26972680}
26982681
26992682#ifdef BENCHMARK
0 commit comments