red-arrow 24.0.0 → 25.0.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e8464767793fb8efd382689c8ca939af17fdb052f462885efb0461d07d905d18
4
- data.tar.gz: e6d037e1400af61e90438eaa255c172eaf850b136ea7f8262b6acbd2b41c8126
3
+ metadata.gz: 3bcc0a7ed27a0a90f4a3675b42017107c61d4d5bdb95967accc6f10369bfc288
4
+ data.tar.gz: 73c43b33827350528691b2619574e943a6a56a9c643c4407b8bc25285fb2353f
5
5
  SHA512:
6
- metadata.gz: 0cfab03a5b046c67d892db13cf1cd8d988fd0da9e61e950983dc2c1662c9b25a11ad8fb2e27ca68c7cd34814f208a4a51eda0d689e6aa9c514b82c026797ac7e
7
- data.tar.gz: 22370cbfb633c8efd7d3ef8e8131001ece304d1c2e79e29bbda7eae4095dea0486f79a9253fbf8d586c11389bd2f3c8b38841f90733cb1dfb4787c2a9327fa15
6
+ metadata.gz: 371fd9f9865dbe7977fbdd2efa2ca0b7dacd22bcb78cc8fd37c2609a5d8843a7335a5ef873caaadfac205ed56fd6eef8ffbee61499a22cd6a3ec16682d82029e
7
+ data.tar.gz: dc3a6e2e97b9c63af48663dd6d8ee0e8d73348a148c02ae66746dbda93cc2983cd5a97b84c88c784dc7ca513d6e918d3dccf9a13a3a15aabf12c7e8cc4f00acc
@@ -31,6 +31,7 @@
31
31
  # undef private
32
32
  #endif
33
33
 
34
+ #include <cstring>
34
35
  #include <sstream>
35
36
 
36
37
  namespace red_arrow {
@@ -220,6 +221,7 @@ namespace red_arrow {
220
221
  return false;
221
222
  }
222
223
  auto view_ = reinterpret_cast<memory_view *>(view);
224
+ memset(view_, 0, sizeof(memory_view));
223
225
  view_->obj = obj;
224
226
  view_->private_data = new PrivateData();
225
227
  auto array = GARROW_ARRAY(RVAL2GOBJ(obj));
@@ -231,9 +233,6 @@ namespace red_arrow {
231
233
  }
232
234
  view_->readonly = true;
233
235
  view_->ndim = 1;
234
- view_->shape = NULL;
235
- view_->strides = NULL;
236
- view_->sub_offsets = NULL;
237
236
  return true;
238
237
  }
239
238
 
@@ -258,6 +257,7 @@ namespace red_arrow {
258
257
  return false;
259
258
  }
260
259
  auto view_ = reinterpret_cast<memory_view *>(view);
260
+ memset(view_, 0, sizeof(memory_view));
261
261
  view_->obj = obj;
262
262
  auto buffer = GARROW_BUFFER(RVAL2GOBJ(obj));
263
263
  auto arrow_buffer = garrow_buffer_get_raw(buffer);
@@ -275,9 +275,6 @@ namespace red_arrow {
275
275
  view_->byte_size = arrow_buffer->size();
276
276
  view_->readonly = true;
277
277
  view_->ndim = 1;
278
- view_->shape = NULL;
279
- view_->strides = NULL;
280
- view_->sub_offsets = NULL;
281
278
  return true;
282
279
  }
283
280
 
@@ -152,5 +152,70 @@ module Arrow
152
152
  def column_names
153
153
  @column_names ||= columns.collect(&:name)
154
154
  end
155
+
156
+ # Merges columns from the given container or Hash and creates
157
+ # a new container.
158
+ #
159
+ # @param other [Hash, self]
160
+ # The columns to be merged.
161
+ #
162
+ # @return [self]
163
+ def merge(other)
164
+ added_columns = {}
165
+ removed_columns = {}
166
+
167
+ case other
168
+ when Hash
169
+ other.each do |name, value|
170
+ name = name.to_s
171
+ if value
172
+ added_columns[name] = ensure_raw_column(name, value)
173
+ else
174
+ removed_columns[name] = true
175
+ end
176
+ end
177
+ when self.class
178
+ other.columns.each do |column|
179
+ name = column.name
180
+ added_columns[name] = ensure_raw_column(name, column)
181
+ end
182
+ else
183
+ message = "merge target must be Hash or #{self.class}: " +
184
+ "<#{other.inspect}>: #{inspect}"
185
+ raise ArgumentError, message
186
+ end
187
+
188
+ new_columns = []
189
+
190
+ columns.each do |column|
191
+ column_name = column.name
192
+ new_column = added_columns.delete(column_name)
193
+
194
+ if new_column
195
+ new_columns << new_column
196
+ next
197
+ end
198
+
199
+ next if removed_columns.key?(column_name)
200
+
201
+ new_columns << ensure_raw_column(column_name, column)
202
+ end
203
+
204
+ added_columns.each_value do |new_column|
205
+ new_columns << new_column
206
+ end
207
+
208
+ new_fields = []
209
+ new_arrays = []
210
+
211
+ new_columns.each do |new_column|
212
+ new_fields << new_column[:field]
213
+ new_arrays << new_column[:data]
214
+ end
215
+
216
+ merged = self.class.new(new_fields, new_arrays)
217
+ share_input(merged)
218
+ merged
219
+ end
155
220
  end
156
221
  end
@@ -37,7 +37,12 @@ module Arrow
37
37
  super(schema, n_rows, values)
38
38
  when 2
39
39
  schema, data = args
40
- RecordBatchBuilder.build(schema, data)
40
+ schema = Schema.new(schema) unless schema.is_a?(Schema)
41
+ if !data.empty? and data.all? {|array| array.is_a?(Arrow::Array)}
42
+ super(schema, data[0].size, data)
43
+ else
44
+ RecordBatchBuilder.build(schema, data)
45
+ end
41
46
  when 3
42
47
  super
43
48
  else
@@ -75,5 +80,26 @@ module Arrow
75
80
  end
76
81
  super
77
82
  end
83
+
84
+ private
85
+
86
+ def ensure_raw_column(name, data)
87
+ case data
88
+ when Array
89
+ {
90
+ field: Field.new(name, data.value_data_type),
91
+ data: data,
92
+ }
93
+ when Column
94
+ {
95
+ field: data.field,
96
+ data: data.data,
97
+ }
98
+ else
99
+ message = "column must be Arrow::Array or Arrow::Column: " +
100
+ "<#{name}>: <#{data.inspect}>: #{inspect}"
101
+ raise ArgumentError, message
102
+ end
103
+ end
78
104
  end
79
105
  end
@@ -46,16 +46,16 @@ module Arrow
46
46
  # @return [Arrow::SortKey] A new suitable sort key.
47
47
  #
48
48
  # @since 4.0.0
49
- def resolve(target, order=nil)
49
+ def resolve(target, order=nil, null_placement=nil)
50
50
  return target if target.is_a?(self)
51
- new(target, order)
51
+ new(target, order, null_placement)
52
52
  end
53
53
 
54
54
  # @api private
55
55
  def try_convert(value)
56
56
  case value
57
57
  when Symbol, String
58
- new(value.to_s, :ascending)
58
+ new(value.to_s, :ascending, :at_end)
59
59
  else
60
60
  nil
61
61
  end
@@ -71,37 +71,46 @@ module Arrow
71
71
  # @param target [Symbol, String] The name or dot path of the
72
72
  # sort column.
73
73
  #
74
- # If `target` is a String, the first character may be
75
- # processed as the "leading order mark". If the first
76
- # character is `"+"` or `"-"`, they are processed as a leading
77
- # order mark. If the first character is processed as a leading
78
- # order mark, the first character is removed from sort column
79
- # target and corresponding order is used. `"+"` uses ascending
80
- # order and `"-"` uses ascending order.
74
+ # If `target` is a String, it may have prefix markers that specify
75
+ # the sort order and null placement. The format is `[+/-][^/$]column`:
81
76
  #
82
- # If `target` is either not a String or `target` doesn't start
83
- # with the leading order mark, sort column is `target` as-is
84
- # and ascending order is used.
77
+ # - `"+"` prefix means ascending order
78
+ # - `"-"` prefix means descending order
79
+ # - `"^"` prefix means nulls at start
80
+ # - `"$"` prefix means nulls at end
85
81
  #
86
- # @example String without the leading order mark
87
- # key = Arrow::SortKey.new("count")
88
- # key.target # => "count"
89
- # key.order # => Arrow::SortOrder::ASCENDING
82
+ # If `target` is a Symbol, it is converted to String and used as-is
83
+ # (no prefix processing).
90
84
  #
91
- # @example String with the "+" leading order mark
92
- # key = Arrow::SortKey.new("+count")
93
- # key.target # => "count"
94
- # key.order # => Arrow::SortOrder::ASCENDING
85
+ # @example String without any prefix
86
+ # key = Arrow::SortKey.new("count")
87
+ # key.target # => "count"
88
+ # key.order # => Arrow::SortOrder::ASCENDING
89
+ # key.null_placement # => Arrow::NullPlacement::AT_END
95
90
  #
96
- # @example String with the "-" leading order mark
91
+ # @example String with order prefix only
97
92
  # key = Arrow::SortKey.new("-count")
98
- # key.target # => "count"
99
- # key.order # => Arrow::SortOrder::DESCENDING
93
+ # key.target # => "count"
94
+ # key.order # => Arrow::SortOrder::DESCENDING
95
+ # key.null_placement # => Arrow::NullPlacement::AT_END
96
+ #
97
+ # @example String with order and null placement prefixes
98
+ # key = Arrow::SortKey.new("-^count")
99
+ # key.target # => "count"
100
+ # key.order # => Arrow::SortOrder::DESCENDING
101
+ # key.null_placement # => Arrow::NullPlacement::AT_START
100
102
  #
101
- # @example Symbol that starts with "-"
103
+ # @example String with null placement prefix only
104
+ # key = Arrow::SortKey.new("^count")
105
+ # key.target # => "count"
106
+ # key.order # => Arrow::SortOrder::ASCENDING
107
+ # key.null_placement # => Arrow::NullPlacement::AT_START
108
+ #
109
+ # @example Symbol (no prefix processing)
102
110
  # key = Arrow::SortKey.new(:"-count")
103
- # key.target # => "-count"
104
- # key.order # => Arrow::SortOrder::ASCENDING
111
+ # key.target # => "-count"
112
+ # key.order # => Arrow::SortOrder::ASCENDING
113
+ # key.null_placement # => Arrow::NullPlacement::AT_END
105
114
  #
106
115
  # @overload initialize(target, order)
107
116
  #
@@ -122,27 +131,54 @@ module Arrow
122
131
  # key = Arrow::SortKey.new("-count", :ascending)
123
132
  # key.target # => "-count"
124
133
  # key.order # => Arrow::SortOrder::ASCENDING
134
+ # key.null_placement # => Arrow::NullPlacement::AT_END
125
135
  #
126
136
  # @example Order by abbreviated target with Symbol
127
137
  # key = Arrow::SortKey.new("count", :desc)
128
138
  # key.target # => "count"
129
139
  # key.order # => Arrow::SortOrder::DESCENDING
140
+ # key.null_placement # => Arrow::NullPlacement::AT_END
130
141
  #
131
142
  # @example Order by String
132
143
  # key = Arrow::SortKey.new("count", "descending")
133
144
  # key.target # => "count"
134
145
  # key.order # => Arrow::SortOrder::DESCENDING
146
+ # key.null_placement # => Arrow::NullPlacement::AT_END
135
147
  #
136
- # @example Order by Arrow::SortOrder
137
- # key = Arrow::SortKey.new("count", Arrow::SortOrder::DESCENDING)
148
+ # @example Order by Arrow::SortOrder, give null_placement with target
149
+ # key = Arrow::SortKey.new("^count", Arrow::SortOrder::DESCENDING)
138
150
  # key.target # => "count"
139
151
  # key.order # => Arrow::SortOrder::DESCENDING
152
+ # key.null_placement # => Arrow::NullPlacement::AT_START
153
+ #
154
+ # @overload initialize(target, order, null_placement)
155
+ #
156
+ # @param target [Symbol, String] The name or dot path of the
157
+ # sort column.
158
+ #
159
+ # @param order [Symbol, String, Arrow::SortOrder] How to order
160
+ # by this sort key.
161
+ #
162
+ # If this is a Symbol or String, this must be `:ascending`,
163
+ # `"ascending"`, `:asc`, `"asc"`, `:descending`,
164
+ # `"descending"`, `:desc` or `"desc"`.
165
+ #
166
+ # @param null_placement [Symbol, String, Arrow::NullPlacement]
167
+ # Where to place nulls and NaNs. Must be `:at_start`, `"at_start"`,
168
+ # `:at_end`, or `"at_end"`.
169
+ #
170
+ # @example With all explicit parameters
171
+ # key = Arrow::SortKey.new("count", :desc, :at_start)
172
+ # key.target # => "count"
173
+ # key.order # => Arrow::SortOrder::DESCENDING
174
+ # key.null_placement # => Arrow::NullPlacement::AT_START
140
175
  #
141
176
  # @since 4.0.0
142
- def initialize(target, order=nil)
143
- target, order = normalize_target(target, order)
177
+ def initialize(target, order=nil, null_placement=nil)
178
+ target, order, null_placement = normalize_target(target, order, null_placement)
144
179
  order = normalize_order(order) || :ascending
145
- initialize_raw(target, order)
180
+ null_placement = normalize_null_placement(null_placement) || :at_end
181
+ initialize_raw(target, order, null_placement)
146
182
  end
147
183
 
148
184
  # @return [String] The string representation of this sort key. You
@@ -151,37 +187,66 @@ module Arrow
151
187
  #
152
188
  # @example Recreate Arrow::SortKey
153
189
  # key = Arrow::SortKey.new("-count")
154
- # key.to_s # => "-count"
190
+ # key.to_s # => "-$count"
155
191
  # key == Arrow::SortKey.new(key.to_s) # => true
156
192
  #
157
193
  # @since 4.0.0
158
194
  def to_s
195
+ result = ""
159
196
  if order == SortOrder::ASCENDING
160
- "+#{target}"
197
+ result += "+"
198
+ else
199
+ result += "-"
200
+ end
201
+ if null_placement == NullPlacement::AT_START
202
+ result += "^"
161
203
  else
162
- "-#{target}"
204
+ result += "$"
163
205
  end
206
+ result += target
207
+ result
164
208
  end
165
209
 
166
210
  # For backward compatibility
167
211
  alias_method :name, :target
168
212
 
169
213
  private
170
- def normalize_target(target, order)
214
+ # Parse prefix format: [+/-][^/$]column
215
+ # Examples: -$column, +^column, ^column, -column
216
+ #
217
+ # Only strips prefixes if the corresponding parameter is not already set.
218
+ # This preserves backward compatibility where specifying order explicitly
219
+ # means the target is used as-is for order prefixes.
220
+ def normalize_target(target, order, null_placement)
171
221
  case target
172
222
  when Symbol
173
- return target.to_s, order
223
+ return target.to_s, order, null_placement
174
224
  when String
175
- return target, order if order
176
- if target.start_with?("-")
177
- return target[1..-1], order || :descending
178
- elsif target.start_with?("+")
179
- return target[1..-1], order || :ascending
180
- else
181
- return target, order
225
+ remaining = target
226
+
227
+ unless order
228
+ if remaining.start_with?("-")
229
+ order = :descending
230
+ remaining = remaining[1..-1]
231
+ elsif remaining.start_with?("+")
232
+ order = :ascending
233
+ remaining = remaining[1..-1]
234
+ end
235
+ end
236
+
237
+ unless null_placement
238
+ if remaining.start_with?("^")
239
+ null_placement = :at_start
240
+ remaining = remaining[1..-1]
241
+ elsif remaining.start_with?("$")
242
+ null_placement = :at_end
243
+ remaining = remaining[1..-1]
244
+ end
182
245
  end
246
+
247
+ return remaining, order, null_placement
183
248
  else
184
- return target, order
249
+ return target, order, null_placement
185
250
  end
186
251
  end
187
252
 
@@ -195,5 +260,16 @@ module Arrow
195
260
  order
196
261
  end
197
262
  end
263
+
264
+ def normalize_null_placement(null_placement)
265
+ case null_placement
266
+ when :at_end, "at_end"
267
+ :at_end
268
+ when :at_start, "at_start"
269
+ :at_start
270
+ else
271
+ null_placement
272
+ end
273
+ end
198
274
  end
199
275
  end
@@ -102,8 +102,8 @@ module Arrow
102
102
  # options.sort_keys.collect(&:to_s) # => ["-price"]
103
103
  #
104
104
  # @since 4.0.0
105
- def add_sort_key(target, order=nil)
106
- add_sort_key_raw(SortKey.resolve(target, order))
105
+ def add_sort_key(target, order=nil, null_placement=nil)
106
+ add_sort_key_raw(SortKey.resolve(target, order, null_placement))
107
107
  end
108
108
  end
109
109
  end
data/lib/arrow/table.rb CHANGED
@@ -354,60 +354,6 @@ module Arrow
354
354
  sliced_table
355
355
  end
356
356
 
357
- # TODO
358
- #
359
- # @return [Arrow::Table]
360
- def merge(other)
361
- added_columns = {}
362
- removed_columns = {}
363
-
364
- case other
365
- when Hash
366
- other.each do |name, value|
367
- name = name.to_s
368
- if value
369
- added_columns[name] = ensure_raw_column(name, value)
370
- else
371
- removed_columns[name] = true
372
- end
373
- end
374
- when Table
375
- added_columns = {}
376
- other.columns.each do |column|
377
- name = column.name
378
- added_columns[name] = ensure_raw_column(name, column)
379
- end
380
- else
381
- message = "merge target must be Hash or Arrow::Table: " +
382
- "<#{other.inspect}>: #{inspect}"
383
- raise ArgumentError, message
384
- end
385
-
386
- new_columns = []
387
- columns.each do |column|
388
- column_name = column.name
389
- new_column = added_columns.delete(column_name)
390
- if new_column
391
- new_columns << new_column
392
- next
393
- end
394
- next if removed_columns.key?(column_name)
395
- new_columns << ensure_raw_column(column_name, column)
396
- end
397
- added_columns.each do |name, new_column|
398
- new_columns << new_column
399
- end
400
- new_fields = []
401
- new_arrays = []
402
- new_columns.each do |new_column|
403
- new_fields << new_column[:field]
404
- new_arrays << new_column[:data]
405
- end
406
- table = self.class.new(new_fields, new_arrays)
407
- share_input(table)
408
- table
409
- end
410
-
411
357
  alias_method :remove_column_raw, :remove_column
412
358
  def remove_column(name_or_index)
413
359
  case name_or_index
data/lib/arrow/version.rb CHANGED
@@ -16,7 +16,7 @@
16
16
  # under the License.
17
17
 
18
18
  module Arrow
19
- VERSION = "24.0.0"
19
+ VERSION = "25.0.0"
20
20
 
21
21
  module Version
22
22
  numbers, TAG = VERSION.split("-")
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: red-arrow
3
3
  version: !ruby/object:Gem::Version
4
- version: 24.0.0
4
+ version: 25.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - The Apache Software Foundation
@@ -259,7 +259,7 @@ homepage: https://arrow.apache.org/
259
259
  licenses:
260
260
  - Apache-2.0
261
261
  metadata:
262
- msys2_mingw_dependencies: arrow>=24.0.0
262
+ msys2_mingw_dependencies: arrow>=25.0.0
263
263
  rdoc_options: []
264
264
  require_paths:
265
265
  - lib
@@ -274,21 +274,21 @@ required_rubygems_version: !ruby/object:Gem::Requirement
274
274
  - !ruby/object:Gem::Version
275
275
  version: '0'
276
276
  requirements:
277
- - 'system: arrow-glib>=24.0.0: amazon_linux: arrow-glib-devel'
278
- - 'system: arrow-glib>=24.0.0: amazon_linux: https://packages.apache.org/artifactory/arrow/amazon-linux/%{version}/apache-arrow-release-latest.rpm'
279
- - 'system: arrow-glib>=24.0.0: amazon_linux: arrow-glib-devel'
280
- - 'system: arrow-glib>=24.0.0: centos: arrow-glib-devel'
281
- - 'system: arrow-glib>=24.0.0: centos: https://packages.apache.org/artifactory/arrow/centos/%{major_version}-stream/apache-arrow-release-latest.rpm'
282
- - 'system: arrow-glib>=24.0.0: centos: arrow-glib-devel'
283
- - 'system: arrow-glib>=24.0.0: conda: arrow-c-glib'
284
- - 'system: arrow-glib>=24.0.0: debian: libarrow-glib-dev'
285
- - 'system: arrow-glib>=24.0.0: debian: https://packages.apache.org/artifactory/arrow/%{distribution}/apache-arrow-apt-source-latest-%{code_name}.deb'
286
- - 'system: arrow-glib>=24.0.0: debian: libarrow-glib-dev'
287
- - 'system: arrow-glib>=24.0.0: fedora: libarrow-glib-devel'
288
- - 'system: arrow-glib>=24.0.0: homebrew: apache-arrow-glib'
289
- - 'system: arrow-glib>=24.0.0: rhel: arrow-glib-devel'
290
- - 'system: arrow-glib>=24.0.0: rhel: https://packages.apache.org/artifactory/arrow/almalinux/%{major_version}/apache-arrow-release-latest.rpm'
291
- - 'system: arrow-glib>=24.0.0: rhel: arrow-glib-devel'
277
+ - 'system: arrow-glib>=25.0.0: amazon_linux: arrow-glib-devel'
278
+ - 'system: arrow-glib>=25.0.0: amazon_linux: https://packages.apache.org/artifactory/arrow/amazon-linux/%{version}/apache-arrow-release-latest.rpm'
279
+ - 'system: arrow-glib>=25.0.0: amazon_linux: arrow-glib-devel'
280
+ - 'system: arrow-glib>=25.0.0: centos: arrow-glib-devel'
281
+ - 'system: arrow-glib>=25.0.0: centos: https://packages.apache.org/artifactory/arrow/centos/%{major_version}-stream/apache-arrow-release-latest.rpm'
282
+ - 'system: arrow-glib>=25.0.0: centos: arrow-glib-devel'
283
+ - 'system: arrow-glib>=25.0.0: conda: arrow-c-glib'
284
+ - 'system: arrow-glib>=25.0.0: debian: libarrow-glib-dev'
285
+ - 'system: arrow-glib>=25.0.0: debian: https://packages.apache.org/artifactory/arrow/%{distribution}/apache-arrow-apt-source-latest-%{code_name}.deb'
286
+ - 'system: arrow-glib>=25.0.0: debian: libarrow-glib-dev'
287
+ - 'system: arrow-glib>=25.0.0: fedora: libarrow-glib-devel'
288
+ - 'system: arrow-glib>=25.0.0: homebrew: apache-arrow-glib'
289
+ - 'system: arrow-glib>=25.0.0: rhel: arrow-glib-devel'
290
+ - 'system: arrow-glib>=25.0.0: rhel: https://packages.apache.org/artifactory/arrow/almalinux/%{major_version}/apache-arrow-release-latest.rpm'
291
+ - 'system: arrow-glib>=25.0.0: rhel: arrow-glib-devel'
292
292
  rubygems_version: 3.6.7
293
293
  specification_version: 4
294
294
  summary: Red Arrow is the Ruby bindings of Apache Arrow