carray 3.0.3 → 3.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +264 -0
- data/README.md +3 -2
- data/carray.gemspec +1 -1
- data/ext/ca_axis_descriptor.h +27 -24
- data/ext/ca_axis_dispatch.c +1 -6
- data/ext/ca_axis_group.c +27 -27
- data/ext/ca_binop_dispatch.c +1 -29
- data/ext/ca_binop_dispatch.h +0 -1
- data/ext/ca_categorical_iterator.c +205 -134
- data/ext/ca_compare.c +7 -18
- data/ext/ca_group_iter.c +16 -17
- data/ext/ca_kernel_iterator.c +1234 -1994
- data/ext/ca_kernel_iterator.h +391 -437
- data/ext/ca_monop_dispatch.c +82 -59
- data/ext/ca_monop_dispatch.h +1 -0
- data/ext/ca_obj_array.c +96 -39
- data/ext/ca_obj_bincmp.c +24 -21
- data/ext/ca_obj_binop.c +15 -26
- data/ext/ca_obj_bitarray.c +3 -2
- data/ext/ca_obj_bitfield.c +5 -6
- data/ext/ca_obj_block.c +18 -9
- data/ext/ca_obj_byte_swap.c +5 -6
- data/ext/ca_obj_const_string.c +173 -19
- data/ext/ca_obj_face.c +238 -57
- data/ext/ca_obj_face.h +19 -0
- data/ext/ca_obj_fake.c +15 -29
- data/ext/ca_obj_farray.c +6 -3
- data/ext/ca_obj_field.c +17 -5
- data/ext/ca_obj_fixlen_string.c +2 -3
- data/ext/ca_obj_grid.c +406 -132
- data/ext/ca_obj_meld.c +172 -34
- data/ext/ca_obj_moncmp.c +23 -8
- data/ext/ca_obj_monop.c +67 -57
- data/ext/ca_obj_object.c +157 -51
- data/ext/ca_obj_record.c +12 -7
- data/ext/ca_obj_reduce.c +13 -8
- data/ext/ca_obj_refer.c +25 -27
- data/ext/ca_obj_remap.c +30 -9
- data/ext/ca_obj_repeat.c +9 -10
- data/ext/ca_obj_roll.c +6 -5
- data/ext/ca_obj_select.c +14 -9
- data/ext/ca_obj_select_axis.c +15 -47
- data/ext/ca_obj_shift.c +11 -1
- data/ext/ca_obj_stack.c +179 -34
- data/ext/ca_obj_stride.c +162 -115
- data/ext/ca_obj_string.c +71 -4
- data/ext/ca_obj_tile.c +6 -5
- data/ext/ca_obj_time.c +22 -6
- data/ext/ca_obj_timedelta.c +22 -6
- data/ext/ca_obj_transpose.c +5 -3
- data/ext/ca_obj_triop.c +23 -32
- data/ext/ca_obj_window.c +190 -26
- data/ext/ca_sweep_engine.c +2 -2
- data/ext/caframe_csv_reader.c +80 -1
- data/ext/carray.h +181 -75
- data/ext/carray_access.c +184 -96
- data/ext/carray_address_basis.c +343 -87
- data/ext/carray_attribute.c +89 -6
- data/ext/carray_bincount.c +10 -8
- data/ext/carray_broadcast.c +13 -8
- data/ext/carray_build_flags.h +3 -0
- data/ext/carray_call_cfunc.c +108 -0
- data/ext/carray_cast.c +142 -24
- data/ext/carray_cast_func.rb +46 -6
- data/ext/carray_class.c +4 -3
- data/ext/carray_config.h +28 -0
- data/ext/carray_conversion.c +16 -7
- data/ext/carray_copy.c +51 -14
- data/ext/carray_core.c +147 -55
- data/ext/carray_count.c +50 -20
- data/ext/carray_element.c +76 -33
- data/ext/carray_factorize.c +118 -64
- data/ext/carray_generate.c +191 -50
- data/ext/carray_histogram.c +62 -17
- data/ext/carray_hold.c +12 -15
- data/ext/carray_index_classifier.c +388 -176
- data/ext/carray_internal.h +336 -29
- data/ext/carray_kernels_bincmp.c +4453 -0
- data/ext/carray_kernels_binop.c +11368 -0
- data/ext/carray_kernels_init.c +1734 -0
- data/ext/carray_kernels_moncmp.c +2104 -0
- data/ext/carray_kernels_monop.c +18369 -0
- data/ext/carray_kernels_reduce_aggregate.c +23818 -0
- data/ext/carray_kernels_reduce_boolean.c +406 -0
- data/ext/carray_kernels_reduce_cumulative.c +10086 -0
- data/ext/carray_kernels_reduce_extreme.c +17634 -0
- data/ext/carray_kernels_reduce_variance.c +3849 -0
- data/ext/carray_kernels_scan.c +4302 -0
- data/ext/carray_kernels_search.c +33829 -0
- data/ext/carray_kernels_sort.c +10906 -0
- data/ext/carray_kernels_triop.c +1864 -0
- data/ext/carray_key_windows.c +216 -0
- data/ext/carray_lazy.c +170 -111
- data/ext/carray_mask.c +292 -72
- data/ext/carray_median_percentile.c +82 -28
- data/ext/carray_memory_view.c +669 -561
- data/ext/carray_operator.c +124 -47
- data/ext/carray_order.c +384 -76
- data/ext/carray_partition.c +28 -27
- data/ext/carray_random.c +67 -13
- data/ext/carray_round.c +273 -0
- data/ext/carray_scatter.c +63 -38
- data/ext/carray_segment.c +3 -3
- data/ext/carray_slab.c +91 -28
- data/ext/carray_sort.c +35 -35
- data/ext/carray_struct.c +19 -18
- data/ext/carray_test.c +26 -5
- data/ext/carray_undef.c +4 -0
- data/ext/carray_utils.c +246 -45
- data/ext/mk_call_cfunc.rb +19 -2
- data/ext/mkkernel.rb +198 -240
- data/ext/ruby_carray.c +10 -4
- data/ext/version.h +4 -4
- data/lib/carray/attribute.rb +126 -22
- data/lib/carray/autoload_carray.rb +8 -31
- data/lib/carray/autoload_method_extension.rb +14 -5
- data/lib/carray/axis_group.rb +255 -106
- data/lib/carray/basics.rb +78 -10
- data/lib/carray/bincount_nd.rb +12 -2
- data/lib/carray/block_iterator.rb +126 -23
- data/lib/carray/boolean_reduce.rb +17 -17
- data/lib/carray/categorical.rb +165 -43
- data/lib/carray/categorical_iterator.rb +130 -27
- data/lib/carray/complex.rb +5 -5
- data/lib/carray/conditional.rb +67 -18
- data/lib/carray/const_string.rb +14 -5
- data/lib/carray/construct.rb +15 -11
- data/lib/carray/data_type_extension.rb +1 -0
- data/lib/carray/distance_limit.rb +77 -0
- data/lib/carray/fixlen_string.rb +7 -1
- data/lib/carray/frame/column_verbs.rb +70 -0
- data/lib/carray/frame/convert.rb +69 -0
- data/lib/carray/frame/csv_parser.rb +111 -17
- data/lib/carray/frame/describe.rb +3 -2
- data/lib/carray/frame/frame.rb +246 -21
- data/lib/carray/frame/group.rb +510 -95
- data/lib/carray/frame/io.rb +115 -28
- data/lib/carray/frame/join.rb +312 -51
- data/lib/carray/frame/records.rb +83 -7
- data/lib/carray/frame/reshape.rb +42 -35
- data/lib/carray/frame/sort.rb +7 -19
- data/lib/carray/frame/verbs.rb +188 -48
- data/lib/carray/frame/windows.rb +117 -0
- data/lib/carray/frame.rb +2 -0
- data/lib/carray/fuse_source.rb +11 -4
- data/lib/carray/fusion.rb +40 -16
- data/lib/carray/histogram.rb +6 -1
- data/lib/carray/inspect.rb +31 -8
- data/lib/carray/iterator.rb +85 -7
- data/lib/carray/key_windows.rb +620 -0
- data/lib/carray/lazy.rb +182 -183
- data/lib/carray/mask_gap_fill.rb +63 -57
- data/lib/carray/meld_reduce.rb +12 -14
- data/lib/carray/methods/bin.rb +26 -18
- data/lib/carray/methods/bincount.rb +16 -0
- data/lib/carray/methods/bit_string.rb +1 -1
- data/lib/carray/methods/choose.rb +16 -3
- data/lib/carray/methods/composition.rb +3 -1
- data/lib/carray/methods/gather_nd.rb +14 -5
- data/lib/carray/methods/insert_block.rb +2 -2
- data/lib/carray/methods/is_between.rb +59 -0
- data/lib/carray/methods/is_in.rb +53 -36
- data/lib/carray/methods/join.rb +1 -6
- data/lib/carray/methods/lag.rb +49 -0
- data/lib/carray/methods/locate_addr.rb +47 -51
- data/lib/carray/methods/mode.rb +1 -1
- data/lib/carray/methods/nunique.rb +11 -6
- data/lib/carray/methods/resize.rb +3 -3
- data/lib/carray/methods/value_counts.rb +4 -11
- data/lib/carray/record_order.rb +3 -3
- data/lib/carray/rng.rb +3 -0
- data/lib/carray/runtime.rb +53 -8
- data/lib/carray/segment_iterator.rb +313 -82
- data/lib/carray/serialize.rb +24 -10
- data/lib/carray/slab_iterator.rb +50 -0
- data/lib/carray/string.rb +105 -5
- data/lib/carray/string_operation_extension.rb +8 -1
- data/lib/carray/struct.rb +9 -21
- data/lib/carray/struct_builder.rb +19 -8
- data/lib/carray/time.rb +726 -104
- data/lib/carray/window_iterator.rb +122 -16
- data/lib/carray.rb +7 -0
- data/yard-stubs/ca_obj_bitfield.rb +1 -1
- data/yard-stubs/ca_obj_field.rb +4 -0
- data/yard-stubs/ca_obj_grid.rb +21 -10
- data/yard-stubs/ca_obj_refer.rb +2 -1
- data/yard-stubs/ca_obj_roll.rb +2 -2
- data/yard-stubs/ca_obj_shift.rb +5 -1
- data/yard-stubs/ca_obj_tile.rb +1 -1
- data/yard-stubs/ca_obj_window.rb +8 -3
- data/yard-stubs/carray_access.rb +6 -1
- data/yard-stubs/carray_attribute.rb +0 -5
- data/yard-stubs/carray_cast.rb +10 -0
- data/yard-stubs/carray_conversion.rb +2 -1
- data/yard-stubs/carray_copy.rb +4 -2
- data/yard-stubs/carray_count.rb +4 -4
- data/yard-stubs/carray_element.rb +10 -4
- data/yard-stubs/carray_generate.rb +21 -1
- data/yard-stubs/carray_mask.rb +26 -2
- data/yard-stubs/carray_math.rb +27 -1
- data/yard-stubs/carray_median_percentile.rb +5 -2
- data/yard-stubs/carray_memory_view.rb +40 -23
- data/yard-stubs/carray_order.rb +29 -18
- data/yard-stubs/carray_random.rb +13 -4
- data/yard-stubs/carray_scatter.rb +14 -9
- data/yard-stubs/carray_slab.rb +9 -2
- data/yard-stubs/carray_sort.rb +6 -5
- data/yard-stubs/carray_test.rb +5 -3
- metadata +25 -3
- data/lib/carray/arrow_tensor.rb +0 -401
- data/lib/carray/table.rb +0 -108
data/ext/ca_obj_binop.c
CHANGED
|
@@ -177,6 +177,7 @@ ca_binop_setup (CABinOp *ca, CArray *left, CArray *right, uint16_t op_id)
|
|
|
177
177
|
CABinOp *
|
|
178
178
|
ca_binop_new (CArray *left, CArray *right, uint16_t op_id)
|
|
179
179
|
{
|
|
180
|
+
/* check: the setup checks nothing */
|
|
180
181
|
CABinOp *ca = (CABinOp *) ca_array_alloc(CA_OBJ_BINOP, left->ndim);
|
|
181
182
|
ca_binop_setup(ca, left, right, op_id);
|
|
182
183
|
return ca;
|
|
@@ -227,7 +228,7 @@ ca_binop_func_xfer_index (void *ap, ca_size_t *idx, void *data, int dir)
|
|
|
227
228
|
ca_size_t s;
|
|
228
229
|
|
|
229
230
|
if ( dir != CA_XFER_GET ) {
|
|
230
|
-
|
|
231
|
+
ca_refuse_read_only();
|
|
231
232
|
}
|
|
232
233
|
|
|
233
234
|
s = ca->bytes;
|
|
@@ -322,7 +323,7 @@ ca_binop_eval (CABinOp *bo, const ca_lazy_req_t *req, void *data)
|
|
|
322
323
|
boolean8_t *slab_mask = NULL;
|
|
323
324
|
void *mscratch = NULL;
|
|
324
325
|
|
|
325
|
-
if (
|
|
326
|
+
if ( ca_op_raises_on_cell(CA_OP_KIND_BINOP, bo->op_id, bo->data_type) ) {
|
|
326
327
|
CArray *ops[2];
|
|
327
328
|
ops[0] = bo->parent;
|
|
328
329
|
ops[1] = bo->right;
|
|
@@ -356,7 +357,7 @@ ca_binop_func_xfer_stride (void *ap, ca_size_t *starts, ca_size_t *counts,
|
|
|
356
357
|
if ( ca_region_is_empty(((CArray *) ap)->ndim, counts) ) return;
|
|
357
358
|
ca_lazy_req_t req;
|
|
358
359
|
if ( dir != CA_XFER_GET ) {
|
|
359
|
-
|
|
360
|
+
ca_refuse_read_only();
|
|
360
361
|
}
|
|
361
362
|
ca_lazy_req_region(&req, ap, starts, counts, strides);
|
|
362
363
|
ca_binop_eval((CABinOp *) ap, &req, data);
|
|
@@ -370,7 +371,7 @@ ca_binop_func_xfer_addrs (void *ap, ca_size_t n, ca_size_t *addrs,
|
|
|
370
371
|
{
|
|
371
372
|
ca_lazy_req_t req;
|
|
372
373
|
if ( dir != CA_XFER_GET ) {
|
|
373
|
-
|
|
374
|
+
ca_refuse_read_only();
|
|
374
375
|
}
|
|
375
376
|
ca_lazy_req_addrs(&req, n, addrs);
|
|
376
377
|
ca_binop_eval((CABinOp *) ap, &req, data);
|
|
@@ -393,15 +394,7 @@ static void
|
|
|
393
394
|
ca_binop_func_allocate (void *ap)
|
|
394
395
|
{
|
|
395
396
|
CABinOp *ca = (CABinOp *) ap;
|
|
396
|
-
ca->ptr =
|
|
397
|
-
/* CA_OBJECT cells are VALUEs and this buffer is about to be marked as
|
|
398
|
-
soon as the view is, so it must not be handed to the GC as raw
|
|
399
|
-
xmalloc garbage. */
|
|
400
|
-
if ( ca->data_type == CA_OBJECT ) {
|
|
401
|
-
VALUE *p = (VALUE *) ca->ptr;
|
|
402
|
-
ca_size_t i;
|
|
403
|
-
for ( i = 0; i < ca->elements; i++ ) *p++ = Qnil;
|
|
404
|
-
}
|
|
397
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
405
398
|
}
|
|
406
399
|
|
|
407
400
|
static void
|
|
@@ -418,19 +411,11 @@ ca_binop_func_attach (void *ap)
|
|
|
418
411
|
int8_t k;
|
|
419
412
|
ca_size_t s;
|
|
420
413
|
|
|
421
|
-
ca->ptr =
|
|
414
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
422
415
|
|
|
423
416
|
s = ca->bytes;
|
|
424
417
|
for ( k = ca->ndim - 1; k >= 0; k-- ) { native[k] = s; s *= ca->dim[k]; }
|
|
425
418
|
for ( k = 0; k < ca->ndim; k++ ) starts[k] = 0;
|
|
426
|
-
/* CA_OBJECT cells are VALUEs and this buffer is about to be marked as
|
|
427
|
-
soon as the view is, so it must not be handed to the GC as raw
|
|
428
|
-
xmalloc garbage. */
|
|
429
|
-
if ( ca->data_type == CA_OBJECT ) {
|
|
430
|
-
VALUE *p = (VALUE *) ca->ptr;
|
|
431
|
-
ca_size_t i;
|
|
432
|
-
for ( i = 0; i < ca->elements; i++ ) *p++ = Qnil;
|
|
433
|
-
}
|
|
434
419
|
ca_binop_func_xfer_stride(ca, starts, ca->dim, native, ca->ptr, CA_XFER_GET);
|
|
435
420
|
}
|
|
436
421
|
|
|
@@ -452,7 +437,7 @@ NORETURN(static void ca_binop_func_fill_data (void *ap, void *ptr));
|
|
|
452
437
|
static void
|
|
453
438
|
ca_binop_func_fill_data (void *ap, void *ptr)
|
|
454
439
|
{
|
|
455
|
-
|
|
440
|
+
ca_refuse_read_only();
|
|
456
441
|
}
|
|
457
442
|
|
|
458
443
|
/* Build out.mask: the operands' masks ORed on each read (CAMaskOfOperands), so
|
|
@@ -605,8 +590,7 @@ rb_ca_binop_build (VALUE l_cary, VALUE r_cary, uint16_t op_id)
|
|
|
605
590
|
/* No kernel for that data_type (fixlen arithmetic, ...): raise as the
|
|
606
591
|
eager binop does, before a view is built over it. */
|
|
607
592
|
if ( ca_binop_kernel_lookup_vv(op_id, l_in_dt) == ca_binop_not_implement ) {
|
|
608
|
-
|
|
609
|
-
"invalid data_type for binop (not implemented)");
|
|
593
|
+
ca_op_refuse_unimplemented(l_cary, l_in_dt, rb_eCADataTypeError);
|
|
610
594
|
}
|
|
611
595
|
|
|
612
596
|
if ( l_in_dt != l->data_type ) {
|
|
@@ -694,6 +678,7 @@ rb_ca_binop_build (VALUE l_cary, VALUE r_cary, uint16_t op_id)
|
|
|
694
678
|
static VALUE
|
|
695
679
|
rb_ca_binop_s_build (VALUE klass, VALUE l_cary, VALUE r_cary, VALUE op_id_val)
|
|
696
680
|
{
|
|
681
|
+
/* fits: an operation number from the library's own table */
|
|
697
682
|
uint16_t op_id = (uint16_t) NUM2UINT(op_id_val);
|
|
698
683
|
(void) klass;
|
|
699
684
|
return rb_ca_binop_build(l_cary, r_cary, op_id);
|
|
@@ -708,7 +693,7 @@ rb_ca_binop_trapping (VALUE self)
|
|
|
708
693
|
{
|
|
709
694
|
CABinOp *bo;
|
|
710
695
|
TypedData_Get_Struct(self, CABinOp, &cabinop_data_type, bo);
|
|
711
|
-
return
|
|
696
|
+
return ca_op_raises_on_cell(CA_OP_KIND_BINOP, bo->op_id, bo->data_type) ? Qtrue : Qfalse;
|
|
712
697
|
}
|
|
713
698
|
|
|
714
699
|
static VALUE
|
|
@@ -729,6 +714,7 @@ rb_ca_binop_right (VALUE self)
|
|
|
729
714
|
}
|
|
730
715
|
|
|
731
716
|
/* Test instrumentation (mirrors CAMonOp counters). */
|
|
717
|
+
#ifdef CARRAY_DEV_BUILD
|
|
732
718
|
static VALUE
|
|
733
719
|
rb_ca_binop_s_reset_scratch_counter (VALUE klass)
|
|
734
720
|
{
|
|
@@ -754,6 +740,7 @@ rb_ca_binop_s_materialise_count (VALUE klass)
|
|
|
754
740
|
{
|
|
755
741
|
return SIZE2NUM(ca_binop_materialise_call_count);
|
|
756
742
|
}
|
|
743
|
+
#endif /* CARRAY_DEV_BUILD */
|
|
757
744
|
|
|
758
745
|
static VALUE
|
|
759
746
|
rb_ca_binop_s_allocate (VALUE klass)
|
|
@@ -834,6 +821,7 @@ Init_ca_obj_binop (void)
|
|
|
834
821
|
rb_ca_binop_right, 0);
|
|
835
822
|
|
|
836
823
|
/* Test instrumentation, not user-facing. */
|
|
824
|
+
#ifdef CARRAY_DEV_BUILD
|
|
837
825
|
rb_define_singleton_method(rb_cCABinOp, "__reset_scratch_counter__",
|
|
838
826
|
rb_ca_binop_s_reset_scratch_counter, 0);
|
|
839
827
|
rb_define_singleton_method(rb_cCABinOp, "__scratch_count__",
|
|
@@ -842,4 +830,5 @@ Init_ca_obj_binop (void)
|
|
|
842
830
|
rb_ca_binop_s_reset_materialise_counter, 0);
|
|
843
831
|
rb_define_singleton_method(rb_cCABinOp, "__materialise_count__",
|
|
844
832
|
rb_ca_binop_s_materialise_count, 0);
|
|
833
|
+
#endif
|
|
845
834
|
}
|
data/ext/ca_obj_bitarray.c
CHANGED
|
@@ -98,6 +98,7 @@ ca_bitarray_setup (CABitarray *ca, CArray *parent)
|
|
|
98
98
|
|
|
99
99
|
/* The bits of one byte would share that byte's one mask cell, so a bit
|
|
100
100
|
view takes no masked array and holds no mask of its own. */
|
|
101
|
+
/* mask: the constructor asks first, before it allocates (ca == NULL) */
|
|
101
102
|
if ( ca_has_mask(parent) ) {
|
|
102
103
|
rb_raise(rb_eArgError,
|
|
103
104
|
"bitarray: the array has a mask, which a bit view can not "
|
|
@@ -395,7 +396,7 @@ ca_bitarray_func_allocate (void *ap)
|
|
|
395
396
|
{
|
|
396
397
|
CABitarray *ca = (CABitarray *) ap;
|
|
397
398
|
ca_attach(ca->parent);
|
|
398
|
-
ca->ptr =
|
|
399
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
399
400
|
}
|
|
400
401
|
|
|
401
402
|
static void
|
|
@@ -403,7 +404,7 @@ ca_bitarray_func_attach (void *ap)
|
|
|
403
404
|
{
|
|
404
405
|
CABitarray *ca = (CABitarray *) ap;
|
|
405
406
|
ca_attach(ca->parent);
|
|
406
|
-
ca->ptr =
|
|
407
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
407
408
|
ca_bitarray_attach(ca);
|
|
408
409
|
}
|
|
409
410
|
|
data/ext/ca_obj_bitfield.c
CHANGED
|
@@ -205,7 +205,7 @@ ca_bitfield_setup (CABitfield *ca, CArray *parent,
|
|
|
205
205
|
data_type = CA_UINT64;
|
|
206
206
|
}
|
|
207
207
|
|
|
208
|
-
|
|
208
|
+
CA_CHECK_BYTES_GIVEN(data_type, bytes);
|
|
209
209
|
|
|
210
210
|
if ( bitlen > bytes * 8 ||
|
|
211
211
|
( ( data_type == CA_BOOLEAN ) && ( bitlen > 1 ) ) ) {
|
|
@@ -273,9 +273,6 @@ ca_bitfield_setup (CABitfield *ca, CArray *parent,
|
|
|
273
273
|
|
|
274
274
|
memcpy(ca->dim, parent->dim, ndim * sizeof(ca_size_t));
|
|
275
275
|
|
|
276
|
-
if ( ca_has_mask(parent) ) {
|
|
277
|
-
ca_create_mask(ca);
|
|
278
|
-
}
|
|
279
276
|
|
|
280
277
|
return 0;
|
|
281
278
|
}
|
|
@@ -288,6 +285,7 @@ ca_bitfield_new (CArray *parent, ca_size_t offset, ca_size_t bitlen,
|
|
|
288
285
|
ca_bitfield_setup(NULL, parent, offset, bitlen, data_type);
|
|
289
286
|
ca = (CABitfield *) ca_array_alloc(CA_OBJ_BITFIELD, parent->ndim);
|
|
290
287
|
ca_bitfield_setup(ca, parent, offset, bitlen, data_type);
|
|
288
|
+
ca_fill_or_free((CArray *) ca, ca_view_inherit_mask, (VALUE) ca);
|
|
291
289
|
return ca;
|
|
292
290
|
}
|
|
293
291
|
|
|
@@ -452,7 +450,7 @@ ca_bitfield_func_allocate (void *ap)
|
|
|
452
450
|
{
|
|
453
451
|
CABitfield *ca = (CABitfield *) ap;
|
|
454
452
|
ca_attach(ca->parent);
|
|
455
|
-
ca->ptr =
|
|
453
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
456
454
|
}
|
|
457
455
|
|
|
458
456
|
static void
|
|
@@ -460,7 +458,7 @@ ca_bitfield_func_attach (void *ap)
|
|
|
460
458
|
{
|
|
461
459
|
CABitfield *ca = (CABitfield *) ap;
|
|
462
460
|
ca_attach(ca->parent);
|
|
463
|
-
ca->ptr =
|
|
461
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
464
462
|
ca_bitfield_attach(ca);
|
|
465
463
|
}
|
|
466
464
|
|
|
@@ -708,6 +706,7 @@ rb_ca_bitfield_initialize_copy (VALUE self, VALUE other)
|
|
|
708
706
|
}
|
|
709
707
|
ca_bitfield_setup(ca, cs->parent, cs->bit_start, cs->bit_length,
|
|
710
708
|
cs->data_type);
|
|
709
|
+
ca_view_inherit_mask((VALUE) ca);
|
|
711
710
|
|
|
712
711
|
return self;
|
|
713
712
|
}
|
data/ext/ca_obj_block.c
CHANGED
|
@@ -124,6 +124,12 @@ ca_block_setup (CABlock *ca, CArray *parent, int8_t ndim, ca_size_t *dim,
|
|
|
124
124
|
}
|
|
125
125
|
}
|
|
126
126
|
|
|
127
|
+
/* ca == NULL asks for the checks above only, so that a constructor can
|
|
128
|
+
run them before it allocates. */
|
|
129
|
+
if ( ca == NULL ) {
|
|
130
|
+
return 0;
|
|
131
|
+
}
|
|
132
|
+
|
|
127
133
|
/* strides[k] = step[k] * Pi_{j>k} size0[j] * parent->bytes */
|
|
128
134
|
suffix = parent->bytes;
|
|
129
135
|
for (i = ndim - 1; i >= 0; i--) {
|
|
@@ -141,10 +147,9 @@ ca_block_setup (CABlock *ca, CArray *parent, int8_t ndim, ca_size_t *dim,
|
|
|
141
147
|
}
|
|
142
148
|
}
|
|
143
149
|
|
|
144
|
-
/*
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
ca_block_func_create_mask reads those tail fields.
|
|
150
|
+
/* The CABlock tail (offset / start / step / count / size0) is filled
|
|
151
|
+
here; ca_block_func_create_mask reads it when the constructor takes
|
|
152
|
+
the parent's mask (ca_view_inherit_mask) after this setup.
|
|
148
153
|
|
|
149
154
|
Pool path: start/step/count/size0 already point into _pool (wired
|
|
150
155
|
by ca_block_pool_init); only memcpy the values. Non-pool path:
|
|
@@ -161,10 +166,10 @@ ca_block_setup (CABlock *ca, CArray *parent, int8_t ndim, ca_size_t *dim,
|
|
|
161
166
|
memcpy(ca->count, count, ndim * sizeof(ca_size_t));
|
|
162
167
|
memcpy(ca->size0, dim, ndim * sizeof(ca_size_t));
|
|
163
168
|
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
169
|
+
ca_stride_setup_view((CAStride *) ca, CA_OBJ_BLOCK, parent,
|
|
170
|
+
parent->data_type, parent->bytes,
|
|
171
|
+
ndim, count, strides,
|
|
172
|
+
base_offset_elements * parent->bytes);
|
|
168
173
|
|
|
169
174
|
return 0;
|
|
170
175
|
}
|
|
@@ -174,8 +179,11 @@ ca_block_new (CArray *parent, int8_t ndim, ca_size_t *dim,
|
|
|
174
179
|
ca_size_t *start, ca_size_t *step, ca_size_t *count,
|
|
175
180
|
ca_size_t offset)
|
|
176
181
|
{
|
|
177
|
-
CABlock *ca
|
|
182
|
+
CABlock *ca;
|
|
183
|
+
ca_block_setup(NULL, parent, ndim, dim, start, step, count, offset);
|
|
184
|
+
ca = (CABlock *) ca_array_alloc(CA_OBJ_BLOCK, ndim);
|
|
178
185
|
ca_block_setup(ca, parent, ndim, dim, start, step, count, offset);
|
|
186
|
+
ca_fill_or_free((CArray *) ca, ca_view_inherit_mask, (VALUE) ca);
|
|
179
187
|
return ca;
|
|
180
188
|
}
|
|
181
189
|
|
|
@@ -265,6 +273,7 @@ rb_cb_initialize_copy (VALUE self, VALUE other)
|
|
|
265
273
|
}
|
|
266
274
|
ca_block_setup(ca, cs->parent, cs->ndim, cs->size0,
|
|
267
275
|
cs->start, cs->step, cs->count, cs->offset);
|
|
276
|
+
ca_view_inherit_mask((VALUE) ca);
|
|
268
277
|
rb_ca_set_parent(self, rb_ca_parent(other));
|
|
269
278
|
return self;
|
|
270
279
|
}
|
data/ext/ca_obj_byte_swap.c
CHANGED
|
@@ -193,7 +193,7 @@ VALUE rb_cCAByteSwap;
|
|
|
193
193
|
int
|
|
194
194
|
ca_byte_swap_setup (CAByteSwap *ca, CArray *parent, VALUE data_class)
|
|
195
195
|
{
|
|
196
|
-
|
|
196
|
+
CA_CHECK_DATA_TYPE_GIVEN(parent->data_type);
|
|
197
197
|
|
|
198
198
|
if ( parent->data_type == CA_OBJECT ) {
|
|
199
199
|
rb_raise(rb_eCADataTypeError, "object array can't be byte-swapped");
|
|
@@ -223,9 +223,6 @@ ca_byte_swap_setup (CAByteSwap *ca, CArray *parent, VALUE data_class)
|
|
|
223
223
|
ca->nosync = 0;
|
|
224
224
|
ca->data_class = data_class; /* Qnil if parent has no data_class */
|
|
225
225
|
|
|
226
|
-
if ( ca_has_mask(parent) ) {
|
|
227
|
-
ca_create_mask(ca);
|
|
228
|
-
}
|
|
229
226
|
if ( ca_is_scalar(parent) ) {
|
|
230
227
|
ca_set_flag(ca, CA_FLAG_SCALAR);
|
|
231
228
|
}
|
|
@@ -240,6 +237,7 @@ ca_byte_swap_new (CArray *parent, VALUE data_class)
|
|
|
240
237
|
ca_byte_swap_setup(NULL, parent, data_class);
|
|
241
238
|
ca = (CAByteSwap *) ca_array_alloc(CA_OBJ_BYTE_SWAP, parent->ndim);
|
|
242
239
|
ca_byte_swap_setup(ca, parent, data_class);
|
|
240
|
+
ca_fill_or_free((CArray *) ca, ca_view_inherit_mask, (VALUE) ca);
|
|
243
241
|
return ca;
|
|
244
242
|
}
|
|
245
243
|
|
|
@@ -464,7 +462,7 @@ ca_byte_swap_func_allocate (void *ap)
|
|
|
464
462
|
{
|
|
465
463
|
CAByteSwap *ca = (CAByteSwap *) ap;
|
|
466
464
|
ca_attach(ca->parent);
|
|
467
|
-
ca->ptr =
|
|
465
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
468
466
|
}
|
|
469
467
|
|
|
470
468
|
static void
|
|
@@ -472,7 +470,7 @@ ca_byte_swap_func_attach (void *ap)
|
|
|
472
470
|
{
|
|
473
471
|
CAByteSwap *ca = (CAByteSwap *) ap;
|
|
474
472
|
ca_attach(ca->parent);
|
|
475
|
-
ca->ptr =
|
|
473
|
+
ca->ptr = ca_alloc_cells((CArray *) ca);
|
|
476
474
|
memcpy(ca->ptr, ca->parent->ptr, ca_length(ca));
|
|
477
475
|
ca_byte_swap_apply(ca, ca->ptr);
|
|
478
476
|
}
|
|
@@ -664,6 +662,7 @@ rb_ca_byte_swap_initialize_copy (VALUE self, VALUE other)
|
|
|
664
662
|
ca_array_pool_alloc(ca, CA_OBJ_BYTE_SWAP, cs->parent->ndim);
|
|
665
663
|
}
|
|
666
664
|
ca_byte_swap_setup(ca, cs->parent, cs->data_class);
|
|
665
|
+
ca_view_inherit_mask((VALUE) ca);
|
|
667
666
|
return self;
|
|
668
667
|
}
|
|
669
668
|
|
data/ext/ca_obj_const_string.c
CHANGED
|
@@ -31,6 +31,7 @@
|
|
|
31
31
|
--------------------------------------------------------------------------- */
|
|
32
32
|
|
|
33
33
|
#include "carray.h"
|
|
34
|
+
#include "ruby/util.h"
|
|
34
35
|
#include "carray_internal.h"
|
|
35
36
|
#include "ca_obj_face.h"
|
|
36
37
|
#include <ruby/encoding.h>
|
|
@@ -122,6 +123,12 @@ ca_const_string_setup (CAConstString *ca, CArray *parent, VALUE buffer, int enco
|
|
|
122
123
|
"(parent.data_type must be CA_FIXLEN with bytes == 16)");
|
|
123
124
|
}
|
|
124
125
|
|
|
126
|
+
/* ca == NULL asks for the checks above only, so that a constructor can
|
|
127
|
+
run them before it allocates. */
|
|
128
|
+
if ( ca == NULL ) {
|
|
129
|
+
return 0;
|
|
130
|
+
}
|
|
131
|
+
|
|
125
132
|
ca->obj_type = CA_OBJ_CONST_STRING;
|
|
126
133
|
/* FIXLEN surface auto-gates mkkernel numeric dispatch. */
|
|
127
134
|
ca->data_type = CA_FIXLEN;
|
|
@@ -143,9 +150,6 @@ ca_const_string_setup (CAConstString *ca, CArray *parent, VALUE buffer, int enco
|
|
|
143
150
|
ca->buffer = buffer;
|
|
144
151
|
ca->encoding_id = encoding_id;
|
|
145
152
|
|
|
146
|
-
if ( ca_has_mask(parent) ) {
|
|
147
|
-
ca_create_mask((CArray *) ca);
|
|
148
|
-
}
|
|
149
153
|
|
|
150
154
|
if ( ca_is_scalar(parent) ) {
|
|
151
155
|
ca_set_flag(ca, CA_FLAG_SCALAR);
|
|
@@ -160,8 +164,11 @@ ca_const_string_setup (CAConstString *ca, CArray *parent, VALUE buffer, int enco
|
|
|
160
164
|
CAConstString *
|
|
161
165
|
ca_const_string_new (CArray *parent, VALUE buffer, int encoding_id)
|
|
162
166
|
{
|
|
163
|
-
CAConstString *ca
|
|
167
|
+
CAConstString *ca;
|
|
168
|
+
ca_const_string_setup(NULL, parent, buffer, encoding_id);
|
|
169
|
+
ca = (CAConstString *) ca_array_alloc(CA_OBJ_CONST_STRING, parent->ndim);
|
|
164
170
|
ca_const_string_setup(ca, parent, buffer, encoding_id);
|
|
171
|
+
ca_fill_or_free((CArray *) ca, ca_view_inherit_mask, (VALUE) ca);
|
|
165
172
|
return ca;
|
|
166
173
|
}
|
|
167
174
|
|
|
@@ -574,7 +581,9 @@ rb_ca_const_string_copy (VALUE self)
|
|
|
574
581
|
|
|
575
582
|
ca_detach((CArray *) ca);
|
|
576
583
|
|
|
577
|
-
|
|
584
|
+
vout = rb_ca_const_string_wrap(vout, rb_str_freeze(newbuf), ca->encoding_id);
|
|
585
|
+
rb_ca_inherit_attr(vout, self);
|
|
586
|
+
return vout;
|
|
578
587
|
}
|
|
579
588
|
|
|
580
589
|
/* to_ca descends to the same compacting copy. The result is detached
|
|
@@ -649,6 +658,7 @@ ca_const_string_scan_begin_pair (VALUE va, ca_const_string_scan_t *a,
|
|
|
649
658
|
ca_const_string_scan_begin(va, a);
|
|
650
659
|
x.self = vb;
|
|
651
660
|
x.s = b;
|
|
661
|
+
/* protect: ends the first scan, which is not an array */
|
|
652
662
|
rb_protect(ca_const_string_scan_begin_body, (VALUE) &x, &tag);
|
|
653
663
|
if ( tag ) {
|
|
654
664
|
ca_const_string_scan_end(a);
|
|
@@ -894,13 +904,12 @@ rb_ca_const_string_search (VALUE self, VALUE query)
|
|
|
894
904
|
byte-for-byte faithful to `to_object.sort` with no collation
|
|
895
905
|
loss. */
|
|
896
906
|
|
|
897
|
-
/*
|
|
898
|
-
|
|
899
|
-
static ca_const_string_scan_t *ca_const_string_sort_ctx;
|
|
900
|
-
|
|
907
|
+
/* The scan is passed to the comparator, not held in a static: Ractors
|
|
908
|
+
sort at the same time. */
|
|
901
909
|
static int
|
|
902
|
-
ca_const_string_byte_cmp (const void *a, const void *b)
|
|
910
|
+
ca_const_string_byte_cmp (const void *a, const void *b, void *ctx)
|
|
903
911
|
{
|
|
912
|
+
ca_const_string_scan_t *scan = (ca_const_string_scan_t *) ctx;
|
|
904
913
|
ca_size_t ia = *(const ca_size_t *) a;
|
|
905
914
|
ca_size_t ib = *(const ca_size_t *) b;
|
|
906
915
|
/* sort raises on masked input, so record() always sets these here; the
|
|
@@ -908,13 +917,21 @@ ca_const_string_byte_cmp (const void *a, const void *b)
|
|
|
908
917
|
const char *pa = NULL, *pb = NULL;
|
|
909
918
|
int64_t la = 0, lb = 0;
|
|
910
919
|
int c;
|
|
911
|
-
ca_const_string_record(
|
|
912
|
-
ca_const_string_record(
|
|
920
|
+
ca_const_string_record(scan, ia, &pa, &la);
|
|
921
|
+
ca_const_string_record(scan, ib, &pb, &lb);
|
|
913
922
|
c = memcmp(pa, pb, (size_t) (la < lb ? la : lb));
|
|
914
923
|
if ( c != 0 ) return c;
|
|
915
924
|
return (la > lb) - (la < lb);
|
|
916
925
|
}
|
|
917
926
|
|
|
927
|
+
static int
|
|
928
|
+
ca_const_string_index_cmp (const void *a, const void *b)
|
|
929
|
+
{
|
|
930
|
+
ca_size_t ia = *(const ca_size_t *) a;
|
|
931
|
+
ca_size_t ib = *(const ca_size_t *) b;
|
|
932
|
+
return (ia > ib) - (ia < ib);
|
|
933
|
+
}
|
|
934
|
+
|
|
918
935
|
/* compute the ascending sort permutation; raises on masked input (matches
|
|
919
936
|
base CArray#sort). caller xfree()s the returned index array. */
|
|
920
937
|
static ca_size_t *
|
|
@@ -928,9 +945,19 @@ ca_const_string_sort_perm (ca_const_string_scan_t *s)
|
|
|
928
945
|
}
|
|
929
946
|
idx = ALLOC_N(ca_size_t, s->n);
|
|
930
947
|
for ( i = 0; i < s->n; i++ ) idx[i] = i;
|
|
931
|
-
|
|
932
|
-
qsort
|
|
933
|
-
|
|
948
|
+
ruby_qsort(idx, (size_t) s->n, sizeof(ca_size_t), ca_const_string_byte_cmp, s);
|
|
949
|
+
/* qsort is not stable. Equal strings keep their order, as CArray's own
|
|
950
|
+
sort does, so each run of them is put back in position order. Breaking
|
|
951
|
+
the tie inside the comparator instead doubles the sort on columns with
|
|
952
|
+
many repeats. */
|
|
953
|
+
for ( i = 0; i < s->n; ) {
|
|
954
|
+
ca_size_t j = i + 1;
|
|
955
|
+
while ( j < s->n && ca_const_string_byte_cmp(&idx[i], &idx[j], s) == 0 ) j++;
|
|
956
|
+
if ( j - i > 1 ) {
|
|
957
|
+
qsort(idx + i, (size_t) (j - i), sizeof(ca_size_t), ca_const_string_index_cmp);
|
|
958
|
+
}
|
|
959
|
+
i = j;
|
|
960
|
+
}
|
|
934
961
|
return idx;
|
|
935
962
|
}
|
|
936
963
|
|
|
@@ -1005,6 +1032,128 @@ ca_const_string_extremum (VALUE self, int want_max)
|
|
|
1005
1032
|
static VALUE rb_ca_const_string_min (VALUE self) { return ca_const_string_extremum(self, 0); }
|
|
1006
1033
|
static VALUE rb_ca_const_string_max (VALUE self) { return ca_const_string_extremum(self, 1); }
|
|
1007
1034
|
|
|
1035
|
+
/* ------------------------------------------------------------------- */
|
|
1036
|
+
/* Native factorize: categorize's discovery pass, read from the bytes. The
|
|
1037
|
+
storage cells are byte ranges, so the fixlen lane of
|
|
1038
|
+
CArray#__factorize_appearance__ would tell ranges apart, not strings. A
|
|
1039
|
+
String is made per distinct value only, after the scan's window closes. */
|
|
1040
|
+
|
|
1041
|
+
static uint64_t
|
|
1042
|
+
ca_const_string_hash_bytes (const char *p, int64_t len)
|
|
1043
|
+
{
|
|
1044
|
+
uint64_t h = 1469598103934665603ULL; /* FNV-1a */
|
|
1045
|
+
int64_t i;
|
|
1046
|
+
for ( i = 0; i < len; i++ ) {
|
|
1047
|
+
h ^= (unsigned char) p[i];
|
|
1048
|
+
h *= 1099511628211ULL;
|
|
1049
|
+
}
|
|
1050
|
+
return h;
|
|
1051
|
+
}
|
|
1052
|
+
|
|
1053
|
+
/* CAConstString#__factorize_appearance__ -> [codes, levels], as the CArray
|
|
1054
|
+
method answers: codes are the narrowest unsigned type holding the k codes
|
|
1055
|
+
and the type-max sentinel, which masked cells store; levels are the k
|
|
1056
|
+
distinct Strings in first-appearance order. */
|
|
1057
|
+
static VALUE
|
|
1058
|
+
rb_ca_const_string_factorize_appearance (VALUE self)
|
|
1059
|
+
{
|
|
1060
|
+
ca_const_string_scan_t s;
|
|
1061
|
+
CAConstString *ca;
|
|
1062
|
+
volatile VALUE vcodes, levels;
|
|
1063
|
+
CArray *co;
|
|
1064
|
+
uint32_t *codes, *slot;
|
|
1065
|
+
int64_t *lev_start, *lev_len;
|
|
1066
|
+
size_t cap = 16, mask_bits;
|
|
1067
|
+
ca_size_t n, i, k = 0;
|
|
1068
|
+
int8_t code_dt;
|
|
1069
|
+
VALUE slot_holder = 0, start_holder = 0, len_holder = 0;
|
|
1070
|
+
|
|
1071
|
+
TypedData_Get_Struct(self, CAConstString, &catext_data_type, ca);
|
|
1072
|
+
n = ca->elements;
|
|
1073
|
+
if ( (uint64_t) n >= 0xFFFFFFFFULL ) {
|
|
1074
|
+
rb_raise(rb_eArgError, "categorize: too many elements for uint32 codes");
|
|
1075
|
+
}
|
|
1076
|
+
while ( cap < (size_t) n * 2 ) {
|
|
1077
|
+
cap <<= 1;
|
|
1078
|
+
}
|
|
1079
|
+
mask_bits = cap - 1;
|
|
1080
|
+
/* Everything the scan writes is allocated before its window opens, and
|
|
1081
|
+
held by the collector: opening the window reads the offsets, which
|
|
1082
|
+
can raise for a parent that answers in Ruby. */
|
|
1083
|
+
vcodes = rb_carray_new(CA_UINT32, ca->ndim, ca->dim, 0, NULL);
|
|
1084
|
+
TypedData_Get_Struct(vcodes, CArray, &carray_data_type, co);
|
|
1085
|
+
codes = (uint32_t *) co->ptr;
|
|
1086
|
+
slot = ALLOCV_N(uint32_t, slot_holder, cap); /* code + 1; 0 is empty */
|
|
1087
|
+
MEMZERO(slot, uint32_t, cap);
|
|
1088
|
+
lev_start = ALLOCV_N(int64_t, start_holder, n > 0 ? n : 1);
|
|
1089
|
+
lev_len = ALLOCV_N(int64_t, len_holder, n > 0 ? n : 1);
|
|
1090
|
+
|
|
1091
|
+
ca_const_string_scan_begin(self, &s);
|
|
1092
|
+
for ( i = 0; i < s.n; i++ ) {
|
|
1093
|
+
const char *p;
|
|
1094
|
+
int64_t len;
|
|
1095
|
+
size_t j;
|
|
1096
|
+
if ( ! ca_const_string_record(&s, i, &p, &len) ) {
|
|
1097
|
+
codes[i] = 0xFFFFFFFFu;
|
|
1098
|
+
continue;
|
|
1099
|
+
}
|
|
1100
|
+
j = (size_t) ca_const_string_hash_bytes(p, len) & mask_bits;
|
|
1101
|
+
for (;;) {
|
|
1102
|
+
uint32_t c = slot[j];
|
|
1103
|
+
if ( c == 0 ) {
|
|
1104
|
+
lev_start[k] = (int64_t) (p - s.buf);
|
|
1105
|
+
lev_len[k] = len;
|
|
1106
|
+
slot[j] = (uint32_t) (k + 1);
|
|
1107
|
+
codes[i] = (uint32_t) k;
|
|
1108
|
+
k++;
|
|
1109
|
+
break;
|
|
1110
|
+
}
|
|
1111
|
+
if ( lev_len[c - 1] == len && memcmp(s.buf + lev_start[c - 1], p, (size_t) len) == 0 ) {
|
|
1112
|
+
codes[i] = c - 1;
|
|
1113
|
+
break;
|
|
1114
|
+
}
|
|
1115
|
+
j = (j + 1) & mask_bits;
|
|
1116
|
+
}
|
|
1117
|
+
}
|
|
1118
|
+
ca_const_string_scan_end(&s);
|
|
1119
|
+
ALLOCV_END(slot_holder);
|
|
1120
|
+
|
|
1121
|
+
/* The buffer is the column's frozen String, alive past the window. */
|
|
1122
|
+
levels = rb_ary_new_capa(k);
|
|
1123
|
+
{
|
|
1124
|
+
const char *buf = RSTRING_PTR(ca->buffer);
|
|
1125
|
+
rb_encoding *enc = rb_enc_from_index(ca->encoding_id);
|
|
1126
|
+
for ( i = 0; i < k; i++ ) {
|
|
1127
|
+
rb_ary_push(levels, rb_enc_str_new(buf + lev_start[i], lev_len[i], enc));
|
|
1128
|
+
}
|
|
1129
|
+
}
|
|
1130
|
+
ALLOCV_END(start_holder);
|
|
1131
|
+
ALLOCV_END(len_holder);
|
|
1132
|
+
|
|
1133
|
+
if ( k <= 0xFF ) { code_dt = CA_UINT8; }
|
|
1134
|
+
else if ( k <= 0xFFFF ) { code_dt = CA_UINT16; }
|
|
1135
|
+
else { code_dt = CA_UINT32; }
|
|
1136
|
+
if ( code_dt != CA_UINT32 ) {
|
|
1137
|
+
VALUE vnarrow = rb_carray_new(code_dt, ca->ndim, ca->dim, 0, NULL);
|
|
1138
|
+
CArray *cn;
|
|
1139
|
+
TypedData_Get_Struct(vnarrow, CArray, &carray_data_type, cn);
|
|
1140
|
+
if ( code_dt == CA_UINT8 ) {
|
|
1141
|
+
uint8_t *cp = (uint8_t *) cn->ptr;
|
|
1142
|
+
for ( i = 0; i < n; i++ ) {
|
|
1143
|
+
cp[i] = codes[i] == 0xFFFFFFFFu ? (uint8_t) 0xFF : (uint8_t) codes[i];
|
|
1144
|
+
}
|
|
1145
|
+
}
|
|
1146
|
+
else {
|
|
1147
|
+
uint16_t *cp = (uint16_t *) cn->ptr;
|
|
1148
|
+
for ( i = 0; i < n; i++ ) {
|
|
1149
|
+
cp[i] = codes[i] == 0xFFFFFFFFu ? (uint16_t) 0xFFFF : (uint16_t) codes[i];
|
|
1150
|
+
}
|
|
1151
|
+
}
|
|
1152
|
+
vcodes = vnarrow;
|
|
1153
|
+
}
|
|
1154
|
+
return rb_ary_new3(2, vcodes, levels);
|
|
1155
|
+
}
|
|
1156
|
+
|
|
1008
1157
|
/* ------------------------------------------------------------------- */
|
|
1009
1158
|
|
|
1010
1159
|
static VALUE
|
|
@@ -1028,6 +1177,7 @@ rb_ca_const_string_initialize_copy (VALUE self, VALUE other)
|
|
|
1028
1177
|
ca_array_pool_alloc(ca, CA_OBJ_CONST_STRING, cs->parent->ndim);
|
|
1029
1178
|
}
|
|
1030
1179
|
ca_const_string_setup(ca, cs->parent, cs->buffer, cs->encoding_id);
|
|
1180
|
+
ca_view_inherit_mask((VALUE) ca);
|
|
1031
1181
|
return self;
|
|
1032
1182
|
}
|
|
1033
1183
|
|
|
@@ -1080,10 +1230,14 @@ Init_ca_obj_const_string (void)
|
|
|
1080
1230
|
/* Native flat sort permutation / min / max (§3.7), byte-memcmp
|
|
1081
1231
|
comparator. The public ordering surface is built on these in
|
|
1082
1232
|
lib/carray/const_string.rb; see the comment above their definitions. */
|
|
1083
|
-
|
|
1084
|
-
|
|
1085
|
-
|
|
1086
|
-
|
|
1233
|
+
rb_define_private_method(rb_cCAConstString, "sort_addr_by_bytes",
|
|
1234
|
+
rb_ca_const_string_sort_index, 0);
|
|
1235
|
+
rb_define_private_method(rb_cCAConstString, "min_string_by_bytes",
|
|
1236
|
+
rb_ca_const_string_min, 0);
|
|
1237
|
+
rb_define_private_method(rb_cCAConstString, "__factorize_appearance__",
|
|
1238
|
+
rb_ca_const_string_factorize_appearance, 0);
|
|
1239
|
+
rb_define_private_method(rb_cCAConstString, "max_string_by_bytes",
|
|
1240
|
+
rb_ca_const_string_max, 0);
|
|
1087
1241
|
|
|
1088
1242
|
/* Y-pilot: Face-local C-level fast path for per-cell scalar fetch. */
|
|
1089
1243
|
ca_face_register_storage_to_element(CA_OBJ_CONST_STRING, rb_ca_const_string_storage_to_element);
|