numo-narray 0.9.1.4 → 0.9.1.5
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +10 -4
- data/ext/numo/narray/array.c +17 -7
- data/ext/numo/narray/data.c +39 -36
- data/ext/numo/narray/extconf.rb +1 -0
- data/ext/numo/narray/gen/narray_def.rb +4 -0
- data/ext/numo/narray/gen/spec.rb +5 -1
- data/ext/numo/narray/gen/tmpl/accum.c +2 -2
- data/ext/numo/narray/gen/tmpl/accum_arg.c +88 -0
- data/ext/numo/narray/gen/tmpl/accum_binary.c +1 -1
- data/ext/numo/narray/gen/tmpl/accum_index.c +25 -14
- data/ext/numo/narray/gen/tmpl/aref.c +5 -35
- data/ext/numo/narray/gen/tmpl/aset.c +7 -37
- data/ext/numo/narray/gen/tmpl/bincount.c +7 -7
- data/ext/numo/narray/gen/tmpl/clip.c +11 -15
- data/ext/numo/narray/gen/tmpl/cum.c +1 -1
- data/ext/numo/narray/gen/tmpl/each.c +4 -2
- data/ext/numo/narray/gen/tmpl/each_with_index.c +5 -2
- data/ext/numo/narray/gen/tmpl/lib.c +2 -2
- data/ext/numo/narray/gen/tmpl/logseq.c +6 -5
- data/ext/numo/narray/gen/tmpl/map_with_index.c +5 -6
- data/ext/numo/narray/gen/tmpl/median.c +2 -2
- data/ext/numo/narray/gen/tmpl/minmax.c +1 -1
- data/ext/numo/narray/gen/tmpl/poly.c +4 -4
- data/ext/numo/narray/gen/tmpl/qsort.c +1 -1
- data/ext/numo/narray/gen/tmpl/rand.c +8 -6
- data/ext/numo/narray/gen/tmpl/rand_norm.c +18 -16
- data/ext/numo/narray/gen/tmpl/seq.c +5 -4
- data/ext/numo/narray/gen/tmpl/sort.c +3 -3
- data/ext/numo/narray/gen/tmpl/sort_index.c +2 -2
- data/ext/numo/narray/gen/tmpl/store_array.c +14 -2
- data/ext/numo/narray/gen/tmpl/unary_s.c +55 -31
- data/ext/numo/narray/gen/tmpl_bit/aref.c +22 -30
- data/ext/numo/narray/gen/tmpl_bit/aset.c +20 -34
- data/ext/numo/narray/gen/tmpl_bit/binary.c +42 -14
- data/ext/numo/narray/gen/tmpl_bit/bit_count.c +5 -0
- data/ext/numo/narray/gen/tmpl_bit/bit_reduce.c +5 -0
- data/ext/numo/narray/gen/tmpl_bit/store_array.c +14 -2
- data/ext/numo/narray/gen/tmpl_bit/store_bit.c +21 -7
- data/ext/numo/narray/gen/tmpl_bit/unary.c +21 -7
- data/ext/numo/narray/index.c +369 -59
- data/ext/numo/narray/math.c +2 -2
- data/ext/numo/narray/narray.c +45 -27
- data/ext/numo/narray/ndloop.c +2 -2
- data/ext/numo/narray/numo/intern.h +3 -2
- data/ext/numo/narray/numo/narray.h +24 -5
- data/ext/numo/narray/numo/ndloop.h +2 -2
- data/ext/numo/narray/numo/template.h +4 -6
- data/ext/numo/narray/numo/types/complex.h +2 -2
- data/ext/numo/narray/step.c +58 -252
- data/ext/numo/narray/struct.c +2 -2
- data/lib/numo/narray/extra.rb +172 -212
- data/numo-narray.gemspec +9 -5
- metadata +18 -17
data/ext/numo/narray/index.c
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
/*
|
2
2
|
index.c
|
3
|
-
Numerical Array
|
4
|
-
(C)
|
3
|
+
Ruby/Numo::NArray - Numerical Array class for Ruby
|
4
|
+
Copyright (C) 1999-2019 Masahiro TANAKA
|
5
5
|
*/
|
6
6
|
//#define NARRAY_C
|
7
7
|
|
@@ -16,24 +16,6 @@
|
|
16
16
|
#define cIndex numo_cInt32
|
17
17
|
#endif
|
18
18
|
|
19
|
-
// from ruby/enumerator.c
|
20
|
-
struct enumerator {
|
21
|
-
VALUE obj;
|
22
|
-
ID meth;
|
23
|
-
VALUE args;
|
24
|
-
// use only above in this source
|
25
|
-
VALUE fib;
|
26
|
-
VALUE dst;
|
27
|
-
VALUE lookahead;
|
28
|
-
VALUE feedvalue;
|
29
|
-
VALUE stop_exc;
|
30
|
-
VALUE size;
|
31
|
-
// incompatible below depending on ruby version
|
32
|
-
//VALUE procs; // ruby 2.4
|
33
|
-
//rb_enumerator_size_func *size_fn; // ruby 2.1-2.4
|
34
|
-
//VALUE (*size_fn)(ANYARGS); // ruby 2.0
|
35
|
-
};
|
36
|
-
|
37
19
|
// note: the memory refed by this pointer is not freed and causes memroy leak.
|
38
20
|
typedef struct {
|
39
21
|
size_t n; // the number of elements of the dimesnion
|
@@ -80,6 +62,7 @@ static ID id_dup;
|
|
80
62
|
static ID id_bracket;
|
81
63
|
static ID id_shift_left;
|
82
64
|
static ID id_mask;
|
65
|
+
static ID id_where;
|
83
66
|
|
84
67
|
|
85
68
|
static void
|
@@ -142,25 +125,66 @@ na_parse_array(VALUE ary, int orig_dim, ssize_t size, na_index_arg_t *q)
|
|
142
125
|
static void
|
143
126
|
na_parse_narray_index(VALUE a, int orig_dim, ssize_t size, na_index_arg_t *q)
|
144
127
|
{
|
145
|
-
VALUE idx;
|
146
|
-
narray_t *na;
|
147
|
-
narray_data_t *nidx;
|
128
|
+
VALUE idx, cls;
|
129
|
+
narray_t *na, *nidx;
|
148
130
|
size_t k, n;
|
149
|
-
ssize_t *nidxp;
|
150
131
|
|
151
132
|
GetNArray(a,na);
|
152
133
|
if (NA_NDIM(na) != 1) {
|
153
134
|
rb_raise(rb_eIndexError, "should be 1-d NArray");
|
154
135
|
}
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
|
163
|
-
q->idx
|
136
|
+
cls = rb_obj_class(a);
|
137
|
+
if (cls==numo_cBit) {
|
138
|
+
if (NA_SIZE(na) != (size_t)size) {
|
139
|
+
rb_raise(rb_eIndexError, "Bit-NArray size mismatch");
|
140
|
+
}
|
141
|
+
idx = rb_funcall(a,id_where,0);
|
142
|
+
GetNArray(idx,nidx);
|
143
|
+
n = NA_SIZE(nidx);
|
144
|
+
q->idx = ALLOC_N(size_t, n);
|
145
|
+
if (na->type!=NARRAY_DATA_T) {
|
146
|
+
rb_bug("NArray#where returned wrong type of NArray");
|
147
|
+
}
|
148
|
+
if (rb_obj_class(idx)==numo_cInt32) {
|
149
|
+
int32_t *p = (int32_t*)NA_DATA_PTR(nidx);
|
150
|
+
for (k=0; k<n; k++) {
|
151
|
+
q->idx[k] = (size_t)p[k];
|
152
|
+
}
|
153
|
+
} else
|
154
|
+
if (rb_obj_class(idx)==numo_cInt64) {
|
155
|
+
int64_t *p = (int64_t*)NA_DATA_PTR(nidx);
|
156
|
+
for (k=0; k<n; k++) {
|
157
|
+
q->idx[k] = (size_t)p[k];
|
158
|
+
}
|
159
|
+
} else {
|
160
|
+
rb_bug("NArray#where should return Int32 or Int64");
|
161
|
+
}
|
162
|
+
RB_GC_GUARD(idx);
|
163
|
+
} else {
|
164
|
+
n = NA_SIZE(na);
|
165
|
+
q->idx = ALLOC_N(size_t, n);
|
166
|
+
if (cls==numo_cInt32 && na->type==NARRAY_DATA_T) {
|
167
|
+
int32_t *p = (int32_t*)NA_DATA_PTR(na);
|
168
|
+
for (k=0; k<n; k++) {
|
169
|
+
q->idx[k] = na_range_check(p[k], size, orig_dim);
|
170
|
+
}
|
171
|
+
} else
|
172
|
+
if (cls==numo_cInt64 && na->type==NARRAY_DATA_T) {
|
173
|
+
int64_t *p = (int64_t*)NA_DATA_PTR(na);
|
174
|
+
for (k=0; k<n; k++) {
|
175
|
+
q->idx[k] = na_range_check(p[k], size, orig_dim);
|
176
|
+
}
|
177
|
+
} else {
|
178
|
+
ssize_t *p;
|
179
|
+
idx = nary_new(cIndex,1,&n);
|
180
|
+
na_store(idx,a);
|
181
|
+
GetNArray(idx,nidx);
|
182
|
+
p = (ssize_t*)NA_DATA_PTR(nidx);
|
183
|
+
for (k=0; k<n; k++) {
|
184
|
+
q->idx[k] = na_range_check(p[k], size, orig_dim);
|
185
|
+
}
|
186
|
+
RB_GC_GUARD(idx);
|
187
|
+
}
|
164
188
|
}
|
165
189
|
q->n = n;
|
166
190
|
q->beg = 0;
|
@@ -173,10 +197,46 @@ static void
|
|
173
197
|
na_parse_range(VALUE range, ssize_t step, int orig_dim, ssize_t size, na_index_arg_t *q)
|
174
198
|
{
|
175
199
|
int n;
|
176
|
-
VALUE excl_end;
|
177
200
|
ssize_t beg, end, beg_orig, end_orig;
|
178
201
|
const char *dot = "..", *edot = "...";
|
179
202
|
|
203
|
+
#ifdef HAVE_RB_ARITHMETIC_SEQUENCE_EXTRACT
|
204
|
+
rb_arithmetic_sequence_components_t x;
|
205
|
+
rb_arithmetic_sequence_extract(range, &x);
|
206
|
+
step = NUM2SSIZET(x.step);
|
207
|
+
|
208
|
+
beg = beg_orig = NUM2SSIZET(x.begin);
|
209
|
+
if (beg < 0) {
|
210
|
+
beg += size;
|
211
|
+
}
|
212
|
+
if (T_NIL == TYPE(x.end)) { // endless range
|
213
|
+
end = size - 1;
|
214
|
+
if (RTEST(x.exclude_end)) {
|
215
|
+
dot = edot;
|
216
|
+
}
|
217
|
+
if (beg < 0 || beg >= size) {
|
218
|
+
rb_raise(rb_eRangeError,
|
219
|
+
"%"SZF"d%s is out of range for size=%"SZF"d",
|
220
|
+
beg_orig, dot, size);
|
221
|
+
}
|
222
|
+
} else {
|
223
|
+
end = end_orig = NUM2SSIZET(x.end);
|
224
|
+
if (end < 0) {
|
225
|
+
end += size;
|
226
|
+
}
|
227
|
+
if (RTEST(x.exclude_end)) {
|
228
|
+
end--;
|
229
|
+
dot = edot;
|
230
|
+
}
|
231
|
+
if (beg < 0 || beg >= size || end < 0 || end >= size) {
|
232
|
+
rb_raise(rb_eRangeError,
|
233
|
+
"%"SZF"d%s%"SZF"d is out of range for size=%"SZF"d",
|
234
|
+
beg_orig, dot, end_orig, size);
|
235
|
+
}
|
236
|
+
}
|
237
|
+
#else
|
238
|
+
VALUE excl_end;
|
239
|
+
|
180
240
|
beg = beg_orig = NUM2SSIZET(rb_funcall(range,id_beg,0));
|
181
241
|
if (beg < 0) {
|
182
242
|
beg += size;
|
@@ -195,17 +255,18 @@ na_parse_range(VALUE range, ssize_t step, int orig_dim, ssize_t size, na_index_a
|
|
195
255
|
"%"SZF"d%s%"SZF"d is out of range for size=%"SZF"d",
|
196
256
|
beg_orig, dot, end_orig, size);
|
197
257
|
}
|
258
|
+
#endif
|
198
259
|
n = (end-beg)/step+1;
|
199
260
|
if (n<0) n=0;
|
200
261
|
na_index_set_step(q,orig_dim,n,beg,step);
|
201
262
|
|
202
263
|
}
|
203
264
|
|
204
|
-
|
205
|
-
|
265
|
+
void
|
266
|
+
na_parse_enumerator_step(VALUE enum_obj, VALUE *pstep )
|
206
267
|
{
|
207
268
|
int len;
|
208
|
-
|
269
|
+
VALUE step;
|
209
270
|
struct enumerator *e;
|
210
271
|
|
211
272
|
if (!RB_TYPE_P(enum_obj, T_DATA)) {
|
@@ -213,26 +274,40 @@ na_parse_enumerator(VALUE enum_obj, int orig_dim, ssize_t size, na_index_arg_t *
|
|
213
274
|
}
|
214
275
|
e = (struct enumerator *)DATA_PTR(enum_obj);
|
215
276
|
|
216
|
-
if (rb_obj_is_kind_of(e->obj, rb_cRange)) {
|
217
|
-
|
218
|
-
|
277
|
+
if (!rb_obj_is_kind_of(e->obj, rb_cRange)) {
|
278
|
+
rb_raise(rb_eTypeError,"not Range object");
|
279
|
+
}
|
280
|
+
|
281
|
+
if (e->meth == id_each) {
|
282
|
+
step = INT2NUM(1);
|
283
|
+
}
|
284
|
+
else if (e->meth == id_step) {
|
285
|
+
if (TYPE(e->args) != T_ARRAY) {
|
286
|
+
rb_raise(rb_eArgError,"no argument for step");
|
219
287
|
}
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
}
|
224
|
-
len = RARRAY_LEN(e->args);
|
225
|
-
if (len != 1) {
|
226
|
-
rb_raise(rb_eArgError,"invalid number of step argument (1 for %d)",len);
|
227
|
-
}
|
228
|
-
step = NUM2SSIZET(RARRAY_AREF(e->args,0));
|
229
|
-
na_parse_range(e->obj, step, orig_dim, size, q);
|
230
|
-
} else {
|
231
|
-
rb_raise(rb_eTypeError,"unknown Range method: %s",rb_id2name(e->meth));
|
288
|
+
len = RARRAY_LEN(e->args);
|
289
|
+
if (len != 1) {
|
290
|
+
rb_raise(rb_eArgError,"invalid number of step argument (1 for %d)",len);
|
232
291
|
}
|
292
|
+
step = RARRAY_AREF(e->args,0);
|
233
293
|
} else {
|
234
|
-
rb_raise(rb_eTypeError,"
|
294
|
+
rb_raise(rb_eTypeError,"unknown Range method: %s",rb_id2name(e->meth));
|
295
|
+
}
|
296
|
+
if (pstep) *pstep = step;
|
297
|
+
}
|
298
|
+
|
299
|
+
static void
|
300
|
+
na_parse_enumerator(VALUE enum_obj, int orig_dim, ssize_t size, na_index_arg_t *q)
|
301
|
+
{
|
302
|
+
VALUE step;
|
303
|
+
struct enumerator *e;
|
304
|
+
|
305
|
+
if (!RB_TYPE_P(enum_obj, T_DATA)) {
|
306
|
+
rb_raise(rb_eTypeError,"wrong argument type (not T_DATA)");
|
235
307
|
}
|
308
|
+
na_parse_enumerator_step(enum_obj, &step);
|
309
|
+
e = (struct enumerator *)DATA_PTR(enum_obj);
|
310
|
+
na_parse_range(e->obj, NUM2SSIZET(step), orig_dim, size, q); // e->obj : Range Object
|
236
311
|
}
|
237
312
|
|
238
313
|
// Analyze *a* which is *i*-th index object and store the information to q
|
@@ -289,14 +364,15 @@ na_index_parse_each(volatile VALUE a, ssize_t size, int i, na_index_arg_t *q)
|
|
289
364
|
if (rb_obj_is_kind_of(a, rb_cRange)) {
|
290
365
|
na_parse_range(a, 1, i, size, q);
|
291
366
|
}
|
367
|
+
#ifdef HAVE_RB_ARITHMETIC_SEQUENCE_EXTRACT
|
368
|
+
else if (rb_obj_is_kind_of(a, rb_cArithSeq)) {
|
369
|
+
//na_parse_arith_seq(a, i, size, q);
|
370
|
+
na_parse_range(a, 1, i, size, q);
|
371
|
+
}
|
372
|
+
#endif
|
292
373
|
else if (rb_obj_is_kind_of(a, rb_cEnumerator)) {
|
293
374
|
na_parse_enumerator(a, i, size, q);
|
294
375
|
}
|
295
|
-
else if (rb_obj_is_kind_of(a, na_cStep)) {
|
296
|
-
ssize_t beg, step, n;
|
297
|
-
nary_step_array_index(a, size, (size_t*)(&n), &beg, &step);
|
298
|
-
na_index_set_step(q,i,n,beg,step);
|
299
|
-
}
|
300
376
|
// NArray index
|
301
377
|
else if (NA_IsNArray(a)) {
|
302
378
|
na_parse_narray_index(a, i, size, q);
|
@@ -308,6 +384,102 @@ na_index_parse_each(volatile VALUE a, ssize_t size, int i, na_index_arg_t *q)
|
|
308
384
|
}
|
309
385
|
|
310
386
|
|
387
|
+
static void
|
388
|
+
na_at_parse_each(volatile VALUE a, ssize_t size, int i, VALUE *idx, ssize_t stride)
|
389
|
+
{
|
390
|
+
na_index_arg_t q;
|
391
|
+
size_t n, k;
|
392
|
+
ssize_t *index;
|
393
|
+
|
394
|
+
// NArray index
|
395
|
+
if (NA_IsNArray(a)) {
|
396
|
+
VALUE a2;
|
397
|
+
narray_t *na, *na2;
|
398
|
+
ssize_t *p2;
|
399
|
+
GetNArray(a,na);
|
400
|
+
if (NA_NDIM(na) != 1) {
|
401
|
+
rb_raise(rb_eIndexError, "should be 1-d NArray");
|
402
|
+
}
|
403
|
+
n = NA_SIZE(na);
|
404
|
+
a2 = nary_new(cIndex,1,&n);
|
405
|
+
na_store(a2,a);
|
406
|
+
GetNArray(a2,na2);
|
407
|
+
p2 = (ssize_t*)NA_DATA_PTR(na2);
|
408
|
+
if (*idx == Qnil) {
|
409
|
+
*idx = a2;
|
410
|
+
for (k=0; k<n; k++) {
|
411
|
+
na_range_check(p2[k],size,i);
|
412
|
+
}
|
413
|
+
} else {
|
414
|
+
narray_t *nidx;
|
415
|
+
GetNArray(*idx,nidx);
|
416
|
+
index = (ssize_t*)NA_DATA_PTR(nidx);
|
417
|
+
if (NA_SIZE(nidx) != n) {
|
418
|
+
rb_raise(nary_eShapeError, "index array sizes mismatch");
|
419
|
+
}
|
420
|
+
for (k=0; k<n; k++) {
|
421
|
+
index[k] += na_range_check(p2[k],size,i) * stride;
|
422
|
+
}
|
423
|
+
}
|
424
|
+
RB_GC_GUARD(a2);
|
425
|
+
return;
|
426
|
+
}
|
427
|
+
else if (TYPE(a) == T_ARRAY) {
|
428
|
+
n = RARRAY_LEN(a);
|
429
|
+
if (*idx == Qnil) {
|
430
|
+
*idx = nary_new(cIndex,1,&n);
|
431
|
+
index = (ssize_t*)na_get_pointer_for_write(*idx); // allocate memory
|
432
|
+
for (k=0; k<n; k++) {
|
433
|
+
index[k] = na_range_check(NUM2SSIZET(RARRAY_AREF(a,k)),size,i);
|
434
|
+
}
|
435
|
+
} else {
|
436
|
+
narray_t *nidx;
|
437
|
+
GetNArray(*idx,nidx);
|
438
|
+
index = (ssize_t*)NA_DATA_PTR(nidx);
|
439
|
+
if (NA_SIZE(nidx) != n) {
|
440
|
+
rb_raise(nary_eShapeError, "index array sizes mismatch");
|
441
|
+
}
|
442
|
+
for (k=0; k<n; k++) {
|
443
|
+
index[k] += na_range_check(NUM2SSIZET(RARRAY_AREF(a,k)),size,i) * stride;
|
444
|
+
}
|
445
|
+
}
|
446
|
+
return;
|
447
|
+
}
|
448
|
+
else if (rb_obj_is_kind_of(a, rb_cRange)) {
|
449
|
+
na_parse_range(a, 1, i, size, &q);
|
450
|
+
}
|
451
|
+
#ifdef HAVE_RB_ARITHMETIC_SEQUENCE_EXTRACT
|
452
|
+
else if (rb_obj_is_kind_of(a, rb_cArithSeq)) {
|
453
|
+
na_parse_range(a, 1, i, size, &q);
|
454
|
+
}
|
455
|
+
#endif
|
456
|
+
else if (rb_obj_is_kind_of(a, rb_cEnumerator)) {
|
457
|
+
na_parse_enumerator(a, i, size, &q);
|
458
|
+
}
|
459
|
+
else {
|
460
|
+
rb_raise(rb_eIndexError, "not allowed type");
|
461
|
+
}
|
462
|
+
|
463
|
+
if (*idx == Qnil) {
|
464
|
+
*idx = nary_new(cIndex,1,&q.n);
|
465
|
+
index = (ssize_t*)na_get_pointer_for_write(*idx); // allocate memory
|
466
|
+
for (k=0; k<q.n; k++) {
|
467
|
+
index[k] = q.beg + q.step*k;
|
468
|
+
}
|
469
|
+
} else {
|
470
|
+
narray_t *nidx;
|
471
|
+
GetNArray(*idx,nidx);
|
472
|
+
index = (ssize_t*)NA_DATA_PTR(nidx);
|
473
|
+
if (NA_SIZE(nidx) != q.n) {
|
474
|
+
rb_raise(nary_eShapeError, "index array sizes mismatch");
|
475
|
+
}
|
476
|
+
for (k=0; k<q.n; k++) {
|
477
|
+
index[k] += (q.beg + q.step*k) * stride;
|
478
|
+
}
|
479
|
+
}
|
480
|
+
}
|
481
|
+
|
482
|
+
|
311
483
|
static size_t
|
312
484
|
na_index_parse_args(VALUE args, narray_t *na, na_index_arg_t *q, int ndim)
|
313
485
|
{
|
@@ -574,7 +746,7 @@ VALUE na_aref_md_protected(VALUE data_value)
|
|
574
746
|
|
575
747
|
na_alloc_shape((narray_t*)na2, ndim_new);
|
576
748
|
|
577
|
-
na2->stridx =
|
749
|
+
na2->stridx = ZALLOC_N(stridx_t,ndim_new);
|
578
750
|
|
579
751
|
elmsz = nary_element_stride(self);
|
580
752
|
|
@@ -842,11 +1014,148 @@ static VALUE na_slice(int argc, VALUE *argv, VALUE self)
|
|
842
1014
|
return na_aref_main(argc, argv, self, 1, nd);
|
843
1015
|
}
|
844
1016
|
|
1017
|
+
/*
|
1018
|
+
Multi-dimensional element reference.
|
1019
|
+
Returns an element at `dim0`, `dim1`, ... are Numeric indices for each dimension, or returns a NArray View as a sliced array if `dim0`, `dim1`, ... includes other than Numeric index, e.g., Range or Array or true.
|
1020
|
+
@overload [](dim0,...,dimL)
|
1021
|
+
@param [Numeric,Range,Array,Numo::Int32,Numo::Int64,Numo::Bit,TrueClass,FalseClass,Symbol] dim0,...,dimL multi-dimensional indices.
|
1022
|
+
@return [Numeric,Numo::NArray] an element or NArray view.
|
1023
|
+
@see #[]=
|
1024
|
+
@see #at
|
1025
|
+
|
1026
|
+
@example
|
1027
|
+
a = Numo::DFloat.new(4,5).seq
|
1028
|
+
# => Numo::DFloat#shape=[4,5]
|
1029
|
+
# [[0, 1, 2, 3, 4],
|
1030
|
+
# [5, 6, 7, 8, 9],
|
1031
|
+
# [10, 11, 12, 13, 14],
|
1032
|
+
# [15, 16, 17, 18, 19]]
|
1033
|
+
|
1034
|
+
a[1,1]
|
1035
|
+
# => 6.0
|
1036
|
+
|
1037
|
+
a[1..3,1]
|
1038
|
+
# => Numo::DFloat#shape=[3]
|
1039
|
+
# [6, 11, 16]
|
1040
|
+
|
1041
|
+
a[1,[1,3,4]]
|
1042
|
+
# => Numo::DFloat#shape=[3]
|
1043
|
+
# [6, 8, 9]
|
1044
|
+
|
1045
|
+
a[true,2].fill(99)
|
1046
|
+
a
|
1047
|
+
# => Numo::DFloat#shape=[4,5]
|
1048
|
+
# [[0, 1, 99, 3, 4],
|
1049
|
+
# [5, 6, 99, 8, 9],
|
1050
|
+
# [10, 11, 99, 13, 14],
|
1051
|
+
# [15, 16, 99, 18, 19]]
|
1052
|
+
*/
|
1053
|
+
static VALUE na_aref(int argc, VALUE *argv, VALUE self)
|
1054
|
+
{
|
1055
|
+
// implemented in subclasses
|
1056
|
+
return rb_f_notimplement(argc,argv,self);
|
1057
|
+
}
|
1058
|
+
|
1059
|
+
/*
|
1060
|
+
Multi-dimensional element assignment.
|
1061
|
+
Replace element(s) at `dim0`, `dim1`, ... .
|
1062
|
+
Broadcasting mechanism is applied.
|
1063
|
+
@overload []=(dim0,...,dimL,val)
|
1064
|
+
@param [Numeric,Range,Array,Numo::Int32,Numo::Int64,Numo::Bit,TrueClass,FalseClass,Symbol] dim0,...,dimL multi-dimensional indices.
|
1065
|
+
@param [Numeric,Numo::NArray,Array] val Value(s) to be set to self.
|
1066
|
+
@return [Numeric,Numo::NArray,Array] returns `val` (last argument).
|
1067
|
+
@see #[]
|
1068
|
+
@example
|
1069
|
+
a = Numo::DFloat.new(3,4).seq
|
1070
|
+
# => Numo::DFloat#shape=[3,4]
|
1071
|
+
# [[0, 1, 2, 3],
|
1072
|
+
# [4, 5, 6, 7],
|
1073
|
+
# [8, 9, 10, 11]]
|
1074
|
+
|
1075
|
+
a[1,2]=99
|
1076
|
+
a
|
1077
|
+
# => Numo::DFloat#shape=[3,4]
|
1078
|
+
# [[0, 1, 2, 3],
|
1079
|
+
# [4, 5, 99, 7],
|
1080
|
+
# [8, 9, 10, 11]]
|
1081
|
+
|
1082
|
+
a[1,[0,2]] = [101,102]
|
1083
|
+
a
|
1084
|
+
# => Numo::DFloat#shape=[3,4]
|
1085
|
+
# [[0, 1, 2, 3],
|
1086
|
+
# [101, 5, 102, 7],
|
1087
|
+
# [8, 9, 10, 11]]
|
1088
|
+
|
1089
|
+
a[1,true]=99
|
1090
|
+
a
|
1091
|
+
# => Numo::DFloat#shape=[3,4]
|
1092
|
+
# [[0, 1, 2, 3],
|
1093
|
+
# [99, 99, 99, 99],
|
1094
|
+
# [8, 9, 10, 11]]
|
1095
|
+
|
1096
|
+
*/
|
1097
|
+
static VALUE na_aset(int argc, VALUE *argv, VALUE self)
|
1098
|
+
{
|
1099
|
+
// implemented in subclasses
|
1100
|
+
return rb_f_notimplement(argc,argv,self);
|
1101
|
+
}
|
1102
|
+
|
1103
|
+
/*
|
1104
|
+
Multi-dimensional array indexing.
|
1105
|
+
Similar to numpy's tuple indexing, i.e., `a[[1,2,..],[3,4,..]]`
|
1106
|
+
Same as Numo::NArray#[] for one-dimensional NArray.
|
1107
|
+
@overload at(dim0,...,dimL)
|
1108
|
+
@param [Range,Array,Numo::Int32,Numo::Int64] dim0,...,dimL multi-dimensional index arrays.
|
1109
|
+
@return [Numo::NArray] one-dimensional NArray view.
|
1110
|
+
@see #[]
|
1111
|
+
|
1112
|
+
@example
|
1113
|
+
x = Numo::DFloat.new(3,3,3).seq
|
1114
|
+
# => Numo::DFloat#shape=[3,3,3]
|
1115
|
+
# [[[0, 1, 2],
|
1116
|
+
# [3, 4, 5],
|
1117
|
+
# [6, 7, 8]],
|
1118
|
+
# [[9, 10, 11],
|
1119
|
+
# [12, 13, 14],
|
1120
|
+
# [15, 16, 17]],
|
1121
|
+
# [[18, 19, 20],
|
1122
|
+
# [21, 22, 23],
|
1123
|
+
# [24, 25, 26]]]
|
1124
|
+
|
1125
|
+
x.at([0,1,2],[0,1,2],[-1,-2,-3])
|
1126
|
+
# => Numo::DFloat(view)#shape=[3]
|
1127
|
+
# [2, 13, 24]
|
1128
|
+
*/
|
1129
|
+
static VALUE na_at(int argc, VALUE *argv, VALUE self)
|
1130
|
+
{
|
1131
|
+
int i;
|
1132
|
+
size_t n;
|
1133
|
+
ssize_t stride=1;
|
1134
|
+
narray_t *na;
|
1135
|
+
VALUE idx=Qnil;
|
1136
|
+
|
1137
|
+
na_index_arg_to_internal_order(argc, argv, self);
|
1138
|
+
|
1139
|
+
GetNArray(self,na);
|
1140
|
+
if (NA_NDIM(na) != argc) {
|
1141
|
+
rb_raise(rb_eArgError,"the number of argument must be same as dimension");
|
1142
|
+
}
|
1143
|
+
for (i=argc; i>0; ) {
|
1144
|
+
i--;
|
1145
|
+
n = NA_SHAPE(na)[i];
|
1146
|
+
na_at_parse_each(argv[i], n, i, &idx, stride);
|
1147
|
+
stride *= n;
|
1148
|
+
}
|
1149
|
+
return na_aref_main(1, &idx, self, 1, 1);
|
1150
|
+
}
|
845
1151
|
|
846
1152
|
void
|
847
1153
|
Init_nary_index()
|
848
1154
|
{
|
849
1155
|
rb_define_method(cNArray, "slice", na_slice, -1);
|
1156
|
+
rb_define_method(cNArray, "[]", na_aref, -1);
|
1157
|
+
rb_define_method(cNArray, "[]=", na_aset, -1);
|
1158
|
+
rb_define_method(cNArray, "at", na_at, -1);
|
850
1159
|
|
851
1160
|
sym_ast = ID2SYM(rb_intern("*"));
|
852
1161
|
sym_all = ID2SYM(rb_intern("all"));
|
@@ -867,4 +1176,5 @@ Init_nary_index()
|
|
867
1176
|
id_bracket = rb_intern("[]");
|
868
1177
|
id_shift_left = rb_intern("<<");
|
869
1178
|
id_mask = rb_intern("mask");
|
1179
|
+
id_where = rb_intern("where");
|
870
1180
|
}
|