1 /*
2 * Licensed to the Apache Software Foundation (ASF) under one
3 * or more contributor license agreements. See the NOTICE file
4 * distributed with this work for additional information
5 * regarding copyright ownership. The ASF licenses this file
6 * to you under the Apache License, Version 2.0 (the
7 * "License"); you may not use this file except in compliance
8 * with the License. You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing,
13 * software distributed under the License is distributed on an
14 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 * KIND, either express or implied. See the License for the
16 * specific language governing permissions and limitations
17 * under the License.
18 */
19
20 #include <arrow-glib/decimal.hpp>
21 #include <arrow-glib/error.hpp>
22
23 template <typename Decimal>
24 struct DecimalConverter {
25 };
26
27 template <>
28 struct DecimalConverter<arrow::Decimal128> {
29 using ArrowType = arrow::Decimal128;
30 using GArrowType = GArrowDecimal128;
31
32 GArrowType *
new_rawDecimalConverter33 new_raw(std::shared_ptr<ArrowType> *arrow_decimal128)
34 {
35 return garrow_decimal128_new_raw(arrow_decimal128);
36 }
37
38 std::shared_ptr<ArrowType>
get_rawDecimalConverter39 get_raw(GArrowType *decimal128)
40 {
41 return garrow_decimal128_get_raw(decimal128);
42 }
43 };
44
45 template <>
46 struct DecimalConverter<arrow::Decimal256> {
47 using ArrowType = arrow::Decimal256;
48 using GArrowType = GArrowDecimal256;
49
50 GArrowType *
new_rawDecimalConverter51 new_raw(std::shared_ptr<ArrowType> *arrow_decimal256) {
52 return garrow_decimal256_new_raw(arrow_decimal256);
53 }
54
55 std::shared_ptr<ArrowType>
get_rawDecimalConverter56 get_raw(GArrowType *decimal256) {
57 return garrow_decimal256_get_raw(decimal256);
58 }
59 };
60
61 template <typename Decimal>
62 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_new_string(const gchar * data)63 garrow_decimal_new_string(const gchar *data)
64 {
65 auto arrow_decimal = std::make_shared<Decimal>(data);
66 DecimalConverter<Decimal> converter;
67 return converter.new_raw(&arrow_decimal);
68 }
69
70 template <typename Decimal>
71 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_new_integer(const gint64 data)72 garrow_decimal_new_integer(const gint64 data)
73 {
74 auto arrow_decimal = std::make_shared<Decimal>(data);
75 DecimalConverter<Decimal> converter;
76 return converter.new_raw(&arrow_decimal);
77 }
78
79 template <typename Decimal>
80 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_copy(typename DecimalConverter<Decimal>::GArrowType * decimal)81 garrow_decimal_copy(typename DecimalConverter<Decimal>::GArrowType *decimal)
82 {
83 DecimalConverter<Decimal> converter;
84 const auto arrow_decimal = converter.get_raw(decimal);
85 auto arrow_copied_decimal = std::make_shared<Decimal>(*arrow_decimal);
86 return converter.new_raw(&arrow_copied_decimal);
87 }
88
89 template <typename Decimal>
90 gboolean
garrow_decimal_equal(typename DecimalConverter<Decimal>::GArrowType * decimal,typename DecimalConverter<Decimal>::GArrowType * other_decimal)91 garrow_decimal_equal(typename DecimalConverter<Decimal>::GArrowType *decimal,
92 typename DecimalConverter<Decimal>::GArrowType *other_decimal)
93 {
94 DecimalConverter<Decimal> converter;
95 const auto arrow_decimal = converter.get_raw(decimal);
96 const auto arrow_other_decimal = converter.get_raw(other_decimal);
97 return *arrow_decimal == *arrow_other_decimal;
98 }
99
100 template <typename Decimal>
101 gboolean
garrow_decimal_not_equal(typename DecimalConverter<Decimal>::GArrowType * decimal,typename DecimalConverter<Decimal>::GArrowType * other_decimal)102 garrow_decimal_not_equal(typename DecimalConverter<Decimal>::GArrowType *decimal,
103 typename DecimalConverter<Decimal>::GArrowType *other_decimal)
104 {
105 DecimalConverter<Decimal> converter;
106 const auto arrow_decimal = converter.get_raw(decimal);
107 const auto arrow_other_decimal = converter.get_raw(other_decimal);
108 return *arrow_decimal != *arrow_other_decimal;
109 }
110
111 template <typename Decimal>
112 gboolean
garrow_decimal_less_than(typename DecimalConverter<Decimal>::GArrowType * decimal,typename DecimalConverter<Decimal>::GArrowType * other_decimal)113 garrow_decimal_less_than(typename DecimalConverter<Decimal>::GArrowType *decimal,
114 typename DecimalConverter<Decimal>::GArrowType *other_decimal)
115 {
116 DecimalConverter<Decimal> converter;
117 const auto arrow_decimal = converter.get_raw(decimal);
118 const auto arrow_other_decimal = converter.get_raw(other_decimal);
119 return *arrow_decimal < *arrow_other_decimal;
120 }
121
122 template <typename Decimal>
123 gboolean
garrow_decimal_less_than_or_equal(typename DecimalConverter<Decimal>::GArrowType * decimal,typename DecimalConverter<Decimal>::GArrowType * other_decimal)124 garrow_decimal_less_than_or_equal(typename DecimalConverter<Decimal>::GArrowType *decimal,
125 typename DecimalConverter<Decimal>::GArrowType *other_decimal)
126 {
127 DecimalConverter<Decimal> converter;
128 const auto arrow_decimal = converter.get_raw(decimal);
129 const auto arrow_other_decimal = converter.get_raw(other_decimal);
130 return *arrow_decimal <= *arrow_other_decimal;
131 }
132
133 template <typename Decimal>
134 gboolean
garrow_decimal_greater_than(typename DecimalConverter<Decimal>::GArrowType * decimal,typename DecimalConverter<Decimal>::GArrowType * other_decimal)135 garrow_decimal_greater_than(typename DecimalConverter<Decimal>::GArrowType *decimal,
136 typename DecimalConverter<Decimal>::GArrowType *other_decimal)
137 {
138 DecimalConverter<Decimal> converter;
139 const auto arrow_decimal = converter.get_raw(decimal);
140 const auto arrow_other_decimal = converter.get_raw(other_decimal);
141 return *arrow_decimal > *arrow_other_decimal;
142 }
143
144 template <typename Decimal>
145 gboolean
garrow_decimal_greater_than_or_equal(typename DecimalConverter<Decimal>::GArrowType * decimal,typename DecimalConverter<Decimal>::GArrowType * other_decimal)146 garrow_decimal_greater_than_or_equal(typename DecimalConverter<Decimal>::GArrowType *decimal,
147 typename DecimalConverter<Decimal>::GArrowType *other_decimal)
148 {
149 DecimalConverter<Decimal> converter;
150 const auto arrow_decimal = converter.get_raw(decimal);
151 const auto arrow_other_decimal = converter.get_raw(other_decimal);
152 return *arrow_decimal >= *arrow_other_decimal;
153 }
154
155 template <typename Decimal>
156 gchar *
garrow_decimal_to_string_scale(typename DecimalConverter<Decimal>::GArrowType * decimal,gint32 scale)157 garrow_decimal_to_string_scale(typename DecimalConverter<Decimal>::GArrowType *decimal,
158 gint32 scale)
159 {
160 DecimalConverter<Decimal> converter;
161 const auto arrow_decimal = converter.get_raw(decimal);
162 return g_strdup(arrow_decimal->ToString(scale).c_str());
163 }
164
165 template <typename Decimal>
166 gchar *
garrow_decimal_to_string(typename DecimalConverter<Decimal>::GArrowType * decimal)167 garrow_decimal_to_string(typename DecimalConverter<Decimal>::GArrowType *decimal)
168 {
169 DecimalConverter<Decimal> converter;
170 const auto arrow_decimal = converter.get_raw(decimal);
171 return g_strdup(arrow_decimal->ToIntegerString().c_str());
172 }
173
174 template <typename Decimal>
175 GBytes *
garrow_decimal_to_bytes(typename DecimalConverter<Decimal>::GArrowType * decimal)176 garrow_decimal_to_bytes(typename DecimalConverter<Decimal>::GArrowType *decimal)
177 {
178 DecimalConverter<Decimal> converter;
179 const auto arrow_decimal = converter.get_raw(decimal);
180 uint8_t data[DecimalConverter<Decimal>::ArrowType::kBitWidth / 8];
181 arrow_decimal->ToBytes(data);
182 return g_bytes_new(data, sizeof(data));
183 }
184
185 template <typename Decimal>
186 void
garrow_decimal_abs(typename DecimalConverter<Decimal>::GArrowType * decimal)187 garrow_decimal_abs(typename DecimalConverter<Decimal>::GArrowType *decimal)
188 {
189 DecimalConverter<Decimal> converter;
190 auto arrow_decimal = converter.get_raw(decimal);
191 arrow_decimal->Abs();
192 }
193
194 template <typename Decimal>
195 void
garrow_decimal_negate(typename DecimalConverter<Decimal>::GArrowType * decimal)196 garrow_decimal_negate(typename DecimalConverter<Decimal>::GArrowType *decimal)
197 {
198 DecimalConverter<Decimal> converter;
199 auto arrow_decimal = converter.get_raw(decimal);
200 arrow_decimal->Negate();
201 }
202
203 template <typename Decimal>
204 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_plus(typename DecimalConverter<Decimal>::GArrowType * left,typename DecimalConverter<Decimal>::GArrowType * right)205 garrow_decimal_plus(typename DecimalConverter<Decimal>::GArrowType *left,
206 typename DecimalConverter<Decimal>::GArrowType *right)
207 {
208 DecimalConverter<Decimal> converter;
209 auto arrow_left = converter.get_raw(left);
210 auto arrow_right = converter.get_raw(right);
211 auto arrow_decimal = std::make_shared<Decimal>(*arrow_left + *arrow_right);
212 return converter.new_raw(&arrow_decimal);
213 }
214
215 template <typename Decimal>
216 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_minus(typename DecimalConverter<Decimal>::GArrowType * left,typename DecimalConverter<Decimal>::GArrowType * right)217 garrow_decimal_minus(typename DecimalConverter<Decimal>::GArrowType *left,
218 typename DecimalConverter<Decimal>::GArrowType *right)
219 {
220 DecimalConverter<Decimal> converter;
221 auto arrow_left = converter.get_raw(left);
222 auto arrow_right = converter.get_raw(right);
223 auto arrow_decimal = std::make_shared<Decimal>(*arrow_left - *arrow_right);
224 return converter.new_raw(&arrow_decimal);
225 }
226
227 template <typename Decimal>
228 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_multiply(typename DecimalConverter<Decimal>::GArrowType * left,typename DecimalConverter<Decimal>::GArrowType * right)229 garrow_decimal_multiply(typename DecimalConverter<Decimal>::GArrowType *left,
230 typename DecimalConverter<Decimal>::GArrowType *right)
231 {
232 DecimalConverter<Decimal> converter;
233 auto arrow_left = converter.get_raw(left);
234 auto arrow_right = converter.get_raw(right);
235 auto arrow_decimal = std::make_shared<Decimal>(*arrow_left * *arrow_right);
236 return converter.new_raw(&arrow_decimal);
237 }
238
239 template <typename Decimal>
240 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_divide(typename DecimalConverter<Decimal>::GArrowType * left,typename DecimalConverter<Decimal>::GArrowType * right,typename DecimalConverter<Decimal>::GArrowType ** remainder,GError ** error,const gchar * tag)241 garrow_decimal_divide(typename DecimalConverter<Decimal>::GArrowType *left,
242 typename DecimalConverter<Decimal>::GArrowType *right,
243 typename DecimalConverter<Decimal>::GArrowType **remainder,
244 GError **error,
245 const gchar *tag)
246 {
247 DecimalConverter<Decimal> converter;
248 auto arrow_left = converter.get_raw(left);
249 auto arrow_right = converter.get_raw(right);
250 auto arrow_result = arrow_left->Divide(*arrow_right);
251 if (garrow::check(error, arrow_result, tag)) {
252 Decimal arrow_quotient_raw;
253 Decimal arrow_remainder_raw;
254 std::tie(arrow_quotient_raw, arrow_remainder_raw) = *arrow_result;
255 if (remainder) {
256 auto arrow_remainder = std::make_shared<Decimal>(arrow_remainder_raw);
257 *remainder = converter.new_raw(&arrow_remainder);
258 }
259 auto arrow_quotient = std::make_shared<Decimal>(arrow_quotient_raw);
260 return converter.new_raw(&arrow_quotient);
261 } else {
262 if (remainder) {
263 *remainder = NULL;
264 }
265 return NULL;
266 }
267 }
268
269 template <typename Decimal>
270 typename DecimalConverter<Decimal>::GArrowType *
garrow_decimal_rescale(typename DecimalConverter<Decimal>::GArrowType * decimal,gint32 original_scale,gint32 new_scale,GError ** error,const gchar * tag)271 garrow_decimal_rescale(typename DecimalConverter<Decimal>::GArrowType *decimal,
272 gint32 original_scale,
273 gint32 new_scale,
274 GError **error,
275 const gchar *tag)
276 {
277 DecimalConverter<Decimal> converter;
278 auto arrow_decimal = converter.get_raw(decimal);
279 auto arrow_result = arrow_decimal->Rescale(original_scale, new_scale);
280 if (garrow::check(error, arrow_result, tag)) {
281 auto arrow_rescaled_decimal = std::make_shared<Decimal>(*arrow_result);
282 return converter.new_raw(&arrow_rescaled_decimal);
283 } else {
284 return NULL;
285 }
286 }
287
288
289 G_BEGIN_DECLS
290
291 /**
292 * SECTION: decimal
293 * @section_id: decimal
294 * @title: 128-bit and 256-bit decimal classes
295 * @include: arrow-glib/arrow-glib.h
296 *
297 * #GArrowDecimal128 is a 128-bit decimal class.
298 *
299 * #GArrowDecimal256 is a 256-bit decimal class.
300 *
301 * Since: 0.10.0
302 */
303
304 typedef struct GArrowDecimal128Private_ {
305 std::shared_ptr<arrow::Decimal128> decimal128;
306 } GArrowDecimal128Private;
307
308 enum {
309 PROP_DECIMAL128 = 1
310 };
311
G_DEFINE_TYPE_WITH_PRIVATE(GArrowDecimal128,garrow_decimal128,G_TYPE_OBJECT)312 G_DEFINE_TYPE_WITH_PRIVATE(GArrowDecimal128,
313 garrow_decimal128,
314 G_TYPE_OBJECT)
315
316 #define GARROW_DECIMAL128_GET_PRIVATE(obj) \
317 static_cast<GArrowDecimal128Private *>( \
318 garrow_decimal128_get_instance_private( \
319 GARROW_DECIMAL128(obj)))
320
321 static void
322 garrow_decimal128_finalize(GObject *object)
323 {
324 auto priv = GARROW_DECIMAL128_GET_PRIVATE(object);
325
326 priv->decimal128.~shared_ptr();
327
328 G_OBJECT_CLASS(garrow_decimal128_parent_class)->finalize(object);
329 }
330
331 static void
garrow_decimal128_set_property(GObject * object,guint prop_id,const GValue * value,GParamSpec * pspec)332 garrow_decimal128_set_property(GObject *object,
333 guint prop_id,
334 const GValue *value,
335 GParamSpec *pspec)
336 {
337 auto priv = GARROW_DECIMAL128_GET_PRIVATE(object);
338
339 switch (prop_id) {
340 case PROP_DECIMAL128:
341 priv->decimal128 =
342 *static_cast<std::shared_ptr<arrow::Decimal128> *>(g_value_get_pointer(value));
343 break;
344 default:
345 G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
346 break;
347 }
348 }
349
350 static void
garrow_decimal128_init(GArrowDecimal128 * object)351 garrow_decimal128_init(GArrowDecimal128 *object)
352 {
353 auto priv = GARROW_DECIMAL128_GET_PRIVATE(object);
354 new(&priv->decimal128) std::shared_ptr<arrow::Decimal128>;
355 }
356
357 static void
garrow_decimal128_class_init(GArrowDecimal128Class * klass)358 garrow_decimal128_class_init(GArrowDecimal128Class *klass)
359 {
360 GParamSpec *spec;
361
362 auto gobject_class = G_OBJECT_CLASS(klass);
363
364 gobject_class->finalize = garrow_decimal128_finalize;
365 gobject_class->set_property = garrow_decimal128_set_property;
366
367 spec = g_param_spec_pointer("decimal128",
368 "Decimal128",
369 "The raw std::shared<arrow::Decimal128> *",
370 static_cast<GParamFlags>(G_PARAM_WRITABLE |
371 G_PARAM_CONSTRUCT_ONLY));
372 g_object_class_install_property(gobject_class, PROP_DECIMAL128, spec);
373 }
374
375 /**
376 * garrow_decimal128_new_string:
377 * @data: The data of the decimal.
378 *
379 * Returns: A newly created #GArrowDecimal128.
380 *
381 * Since: 0.10.0
382 */
383 GArrowDecimal128 *
garrow_decimal128_new_string(const gchar * data)384 garrow_decimal128_new_string(const gchar *data)
385 {
386 return garrow_decimal_new_string<arrow::Decimal128>(data);
387 }
388
389 /**
390 * garrow_decimal128_new_integer:
391 * @data: The data of the decimal.
392 *
393 * Returns: A newly created #GArrowDecimal128.
394 *
395 * Since: 0.10.0
396 */
397 GArrowDecimal128 *
garrow_decimal128_new_integer(const gint64 data)398 garrow_decimal128_new_integer(const gint64 data)
399 {
400 return garrow_decimal_new_integer<arrow::Decimal128>(data);
401 }
402
403 /**
404 * garrow_decimal128_copy:
405 * @decimal: The decimal to be copied.
406 *
407 * Returns: (transfer full): A copied #GArrowDecimal128.
408 *
409 * Since: 3.0.0
410 */
411 GArrowDecimal128 *
garrow_decimal128_copy(GArrowDecimal128 * decimal)412 garrow_decimal128_copy(GArrowDecimal128 *decimal)
413 {
414 return garrow_decimal_copy<arrow::Decimal128>(decimal);
415 }
416
417 /**
418 * garrow_decimal128_equal:
419 * @decimal: A #GArrowDecimal128.
420 * @other_decimal: A #GArrowDecimal128 to be compared.
421 *
422 * Returns: %TRUE if the decimal is equal to the other decimal, %FALSE
423 * otherwise.
424 *
425 * Since: 0.12.0
426 */
427 gboolean
garrow_decimal128_equal(GArrowDecimal128 * decimal,GArrowDecimal128 * other_decimal)428 garrow_decimal128_equal(GArrowDecimal128 *decimal,
429 GArrowDecimal128 *other_decimal)
430 {
431 return garrow_decimal_equal<arrow::Decimal128>(decimal, other_decimal);
432 }
433
434 /**
435 * garrow_decimal128_not_equal:
436 * @decimal: A #GArrowDecimal128.
437 * @other_decimal: A #GArrowDecimal128 to be compared.
438 *
439 * Returns: %TRUE if the decimal isn't equal to the other decimal,
440 * %FALSE otherwise.
441 *
442 * Since: 0.12.0
443 */
444 gboolean
garrow_decimal128_not_equal(GArrowDecimal128 * decimal,GArrowDecimal128 * other_decimal)445 garrow_decimal128_not_equal(GArrowDecimal128 *decimal,
446 GArrowDecimal128 *other_decimal)
447 {
448 return garrow_decimal_not_equal<arrow::Decimal128>(decimal, other_decimal);
449 }
450
451 /**
452 * garrow_decimal128_less_than:
453 * @decimal: A #GArrowDecimal128.
454 * @other_decimal: A #GArrowDecimal128 to be compared.
455 *
456 * Returns: %TRUE if the decimal is less than the other decimal,
457 * %FALSE otherwise.
458 *
459 * Since: 0.12.0
460 */
461 gboolean
garrow_decimal128_less_than(GArrowDecimal128 * decimal,GArrowDecimal128 * other_decimal)462 garrow_decimal128_less_than(GArrowDecimal128 *decimal,
463 GArrowDecimal128 *other_decimal)
464 {
465 return garrow_decimal_less_than<arrow::Decimal128>(decimal, other_decimal);
466 }
467
468 /**
469 * garrow_decimal128_less_than_or_equal:
470 * @decimal: A #GArrowDecimal128.
471 * @other_decimal: A #GArrowDecimal128 to be compared.
472 *
473 * Returns: %TRUE if the decimal is less than the other decimal
474 * or equal to the other decimal, %FALSE otherwise.
475 *
476 * Since: 0.12.0
477 */
478 gboolean
garrow_decimal128_less_than_or_equal(GArrowDecimal128 * decimal,GArrowDecimal128 * other_decimal)479 garrow_decimal128_less_than_or_equal(GArrowDecimal128 *decimal,
480 GArrowDecimal128 *other_decimal)
481 {
482 return garrow_decimal_less_than_or_equal<arrow::Decimal128>(decimal, other_decimal);
483 }
484
485 /**
486 * garrow_decimal128_greater_than:
487 * @decimal: A #GArrowDecimal128.
488 * @other_decimal: A #GArrowDecimal128 to be compared.
489 *
490 * Returns: %TRUE if the decimal is greater than the other decimal,
491 * %FALSE otherwise.
492 *
493 * Since: 0.12.0
494 */
495 gboolean
garrow_decimal128_greater_than(GArrowDecimal128 * decimal,GArrowDecimal128 * other_decimal)496 garrow_decimal128_greater_than(GArrowDecimal128 *decimal,
497 GArrowDecimal128 *other_decimal)
498 {
499 return garrow_decimal_greater_than<arrow::Decimal128>(decimal, other_decimal);
500 }
501
502 /**
503 * garrow_decimal128_greater_than_or_equal:
504 * @decimal: A #GArrowDecimal128.
505 * @other_decimal: A #GArrowDecimal128 to be compared.
506 *
507 * Returns: %TRUE if the decimal is greater than the other decimal
508 * or equal to the other decimal, %FALSE otherwise.
509 *
510 * Since: 0.12.0
511 */
512 gboolean
garrow_decimal128_greater_than_or_equal(GArrowDecimal128 * decimal,GArrowDecimal128 * other_decimal)513 garrow_decimal128_greater_than_or_equal(GArrowDecimal128 *decimal,
514 GArrowDecimal128 *other_decimal)
515 {
516 return garrow_decimal_greater_than_or_equal<arrow::Decimal128>(decimal, other_decimal);
517 }
518
519 /**
520 * garrow_decimal128_to_string_scale:
521 * @decimal: A #GArrowDecimal128.
522 * @scale: The scale of the decimal.
523 *
524 * Returns: The string representation of the decimal.
525 *
526 * It should be freed with g_free() when no longer needed.
527 *
528 * Since: 0.10.0
529 */
530 gchar *
garrow_decimal128_to_string_scale(GArrowDecimal128 * decimal,gint32 scale)531 garrow_decimal128_to_string_scale(GArrowDecimal128 *decimal, gint32 scale)
532 {
533 return garrow_decimal_to_string_scale<arrow::Decimal128>(decimal, scale);
534 }
535
536 /**
537 * garrow_decimal128_to_string:
538 * @decimal: A #GArrowDecimal128.
539 *
540 * Returns: The string representation of the decimal.
541 *
542 * It should be freed with g_free() when no longer needed.
543 *
544 * Since: 0.10.0
545 */
546 gchar *
garrow_decimal128_to_string(GArrowDecimal128 * decimal)547 garrow_decimal128_to_string(GArrowDecimal128 *decimal)
548 {
549 return garrow_decimal_to_string<arrow::Decimal128>(decimal);
550 }
551
552 /**
553 * garrow_decimal128_to_bytes:
554 * @decimal: A #GArrowDecimal128.
555 *
556 * Returns: (transfer full): The binary representation of the decimal.
557 *
558 * Since: 3.0.0
559 */
560 GBytes *
garrow_decimal128_to_bytes(GArrowDecimal128 * decimal)561 garrow_decimal128_to_bytes(GArrowDecimal128 *decimal)
562 {
563 return garrow_decimal_to_bytes<arrow::Decimal128>(decimal);
564 }
565
566 /**
567 * garrow_decimal128_abs:
568 * @decimal: A #GArrowDecimal128.
569 *
570 * Computes the absolute value of the @decimal destructively.
571 *
572 * Since: 0.10.0
573 */
574 void
garrow_decimal128_abs(GArrowDecimal128 * decimal)575 garrow_decimal128_abs(GArrowDecimal128 *decimal)
576 {
577 garrow_decimal_abs<arrow::Decimal128>(decimal);
578 }
579
580 /**
581 * garrow_decimal128_negate:
582 * @decimal: A #GArrowDecimal128.
583 *
584 * Negate the current value of the @decimal destructively.
585 *
586 * Since: 0.10.0
587 */
588 void
garrow_decimal128_negate(GArrowDecimal128 * decimal)589 garrow_decimal128_negate(GArrowDecimal128 *decimal)
590 {
591 garrow_decimal_negate<arrow::Decimal128>(decimal);
592 }
593
594 /**
595 * garrow_decimal128_to_integer:
596 * @decimal: A #GArrowDecimal128.
597 *
598 * Returns: The 64-bit integer representation of the decimal.
599 *
600 * Since: 0.10.0
601 */
602 gint64
garrow_decimal128_to_integer(GArrowDecimal128 * decimal)603 garrow_decimal128_to_integer(GArrowDecimal128 *decimal)
604 {
605 auto arrow_decimal = garrow_decimal128_get_raw(decimal);
606 return static_cast<int64_t>(*arrow_decimal);
607 }
608
609 /**
610 * garrow_decimal128_plus:
611 * @left: A #GArrowDecimal128.
612 * @right: A #GArrowDecimal128.
613 *
614 * Returns: (transfer full): The added value of these decimals.
615 *
616 * Since: 0.11.0
617 */
618 GArrowDecimal128 *
garrow_decimal128_plus(GArrowDecimal128 * left,GArrowDecimal128 * right)619 garrow_decimal128_plus(GArrowDecimal128 *left,
620 GArrowDecimal128 *right)
621 {
622 return garrow_decimal_plus<arrow::Decimal128>(left, right);
623 }
624
625 /**
626 * garrow_decimal128_minus:
627 * @left: A #GArrowDecimal128.
628 * @right: A #GArrowDecimal128.
629 *
630 * Returns: (transfer full): The subtracted value of these decimals.
631 *
632 * Since: 0.11.0
633 */
634 GArrowDecimal128 *
garrow_decimal128_minus(GArrowDecimal128 * left,GArrowDecimal128 * right)635 garrow_decimal128_minus(GArrowDecimal128 *left,
636 GArrowDecimal128 *right)
637 {
638 return garrow_decimal_minus<arrow::Decimal128>(left, right);
639 }
640
641 /**
642 * garrow_decimal128_multiply:
643 * @left: A #GArrowDecimal128.
644 * @right: A #GArrowDecimal128.
645 *
646 * Returns: (transfer full): The multiplied value of these decimals.
647 *
648 * Since: 0.11.0
649 */
650 GArrowDecimal128 *
garrow_decimal128_multiply(GArrowDecimal128 * left,GArrowDecimal128 * right)651 garrow_decimal128_multiply(GArrowDecimal128 *left,
652 GArrowDecimal128 *right)
653 {
654 return garrow_decimal_multiply<arrow::Decimal128>(left, right);
655 }
656
657 /**
658 * garrow_decimal128_divide:
659 * @left: A #GArrowDecimal128.
660 * @right: A #GArrowDecimal128.
661 * @remainder: (out) (nullable): A return location for the remainder
662 * value of these decimals. The returned #GArrowDecimal128 be
663 * unreferred with g_object_unref() when no longer needed.
664 * @error: (nullable): Return location for a #GError or %NULL.
665 *
666 * Returns: (nullable) (transfer full): The divided value of
667 * these decimals or %NULL on error.
668 *
669 * Since: 0.11.0
670 */
671 GArrowDecimal128 *
garrow_decimal128_divide(GArrowDecimal128 * left,GArrowDecimal128 * right,GArrowDecimal128 ** remainder,GError ** error)672 garrow_decimal128_divide(GArrowDecimal128 *left,
673 GArrowDecimal128 *right,
674 GArrowDecimal128 **remainder,
675 GError **error)
676 {
677 return garrow_decimal_divide<arrow::Decimal128>(left,
678 right,
679 remainder,
680 error,
681 "[decimal128][divide]");
682 }
683
684 /**
685 * garrow_decimal128_rescale:
686 * @decimal: A #GArrowDecimal128.
687 * @original_scale: A scale to be converted from.
688 * @new_scale: A scale to be converted to.
689 * @error: (nullable): Return location for a #GError or %NULL.
690 *
691 * Returns: (nullable) (transfer full): The rescaled decimal or %NULL on error.
692 *
693 * Since: 0.15.0
694 */
695 GArrowDecimal128 *
garrow_decimal128_rescale(GArrowDecimal128 * decimal,gint32 original_scale,gint32 new_scale,GError ** error)696 garrow_decimal128_rescale(GArrowDecimal128 *decimal,
697 gint32 original_scale,
698 gint32 new_scale,
699 GError **error)
700 {
701 return garrow_decimal_rescale<arrow::Decimal128>(decimal,
702 original_scale,
703 new_scale,
704 error,
705 "[decimal128][rescale]");
706 }
707
708
709 typedef struct GArrowDecimal256Private_ {
710 std::shared_ptr<arrow::Decimal256> decimal256;
711 } GArrowDecimal256Private;
712
713 enum {
714 PROP_DECIMAL256 = 1
715 };
716
G_DEFINE_TYPE_WITH_PRIVATE(GArrowDecimal256,garrow_decimal256,G_TYPE_OBJECT)717 G_DEFINE_TYPE_WITH_PRIVATE(GArrowDecimal256,
718 garrow_decimal256,
719 G_TYPE_OBJECT)
720
721 #define GARROW_DECIMAL256_GET_PRIVATE(obj) \
722 static_cast<GArrowDecimal256Private *>( \
723 garrow_decimal256_get_instance_private( \
724 GARROW_DECIMAL256(obj)))
725
726 static void
727 garrow_decimal256_finalize(GObject *object)
728 {
729 auto priv = GARROW_DECIMAL256_GET_PRIVATE(object);
730
731 priv->decimal256.~shared_ptr();
732
733 G_OBJECT_CLASS(garrow_decimal256_parent_class)->finalize(object);
734 }
735
736 static void
garrow_decimal256_set_property(GObject * object,guint prop_id,const GValue * value,GParamSpec * pspec)737 garrow_decimal256_set_property(GObject *object,
738 guint prop_id,
739 const GValue *value,
740 GParamSpec *pspec)
741 {
742 auto priv = GARROW_DECIMAL256_GET_PRIVATE(object);
743
744 switch (prop_id) {
745 case PROP_DECIMAL256:
746 priv->decimal256 =
747 *static_cast<std::shared_ptr<arrow::Decimal256> *>(g_value_get_pointer(value));
748 break;
749 default:
750 G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
751 break;
752 }
753 }
754
755 static void
garrow_decimal256_init(GArrowDecimal256 * object)756 garrow_decimal256_init(GArrowDecimal256 *object)
757 {
758 auto priv = GARROW_DECIMAL256_GET_PRIVATE(object);
759 new(&priv->decimal256) std::shared_ptr<arrow::Decimal256>;
760 }
761
762 static void
garrow_decimal256_class_init(GArrowDecimal256Class * klass)763 garrow_decimal256_class_init(GArrowDecimal256Class *klass)
764 {
765 GParamSpec *spec;
766
767 auto gobject_class = G_OBJECT_CLASS(klass);
768
769 gobject_class->finalize = garrow_decimal256_finalize;
770 gobject_class->set_property = garrow_decimal256_set_property;
771
772 spec = g_param_spec_pointer("decimal256",
773 "Decimal256",
774 "The raw std::shared<arrow::Decimal256> *",
775 static_cast<GParamFlags>(G_PARAM_WRITABLE |
776 G_PARAM_CONSTRUCT_ONLY));
777 g_object_class_install_property(gobject_class, PROP_DECIMAL256, spec);
778 }
779
780 /**
781 * garrow_decimal256_new_string:
782 * @data: The data of the decimal.
783 *
784 * Returns: A newly created #GArrowDecimal256.
785 *
786 * Since: 3.0.0
787 */
788 GArrowDecimal256 *
garrow_decimal256_new_string(const gchar * data)789 garrow_decimal256_new_string(const gchar *data)
790 {
791 return garrow_decimal_new_string<arrow::Decimal256>(data);
792 }
793
794 /**
795 * garrow_decimal256_new_integer:
796 * @data: The data of the decimal.
797 *
798 * Returns: A newly created #GArrowDecimal256.
799 *
800 * Since: 3.0.0
801 */
802 GArrowDecimal256 *
garrow_decimal256_new_integer(const gint64 data)803 garrow_decimal256_new_integer(const gint64 data)
804 {
805 return garrow_decimal_new_integer<arrow::Decimal256>(data);
806 }
807
808 /**
809 * garrow_decimal256_copy:
810 * @decimal: The decimal to be copied.
811 *
812 * Returns: (transfer full): A copied #GArrowDecimal256.
813 *
814 * Since: 3.0.0
815 */
816 GArrowDecimal256 *
garrow_decimal256_copy(GArrowDecimal256 * decimal)817 garrow_decimal256_copy(GArrowDecimal256 *decimal)
818 {
819 return garrow_decimal_copy<arrow::Decimal256>(decimal);
820 }
821
822 /**
823 * garrow_decimal256_equal:
824 * @decimal: A #GArrowDecimal256.
825 * @other_decimal: A #GArrowDecimal256 to be compared.
826 *
827 * Returns: %TRUE if the decimal is equal to the other decimal, %FALSE
828 * otherwise.
829 *
830 * Since: 3.0.0
831 */
832 gboolean
garrow_decimal256_equal(GArrowDecimal256 * decimal,GArrowDecimal256 * other_decimal)833 garrow_decimal256_equal(GArrowDecimal256 *decimal,
834 GArrowDecimal256 *other_decimal)
835 {
836 return garrow_decimal_equal<arrow::Decimal256>(decimal, other_decimal);
837 }
838
839 /**
840 * garrow_decimal256_not_equal:
841 * @decimal: A #GArrowDecimal256.
842 * @other_decimal: A #GArrowDecimal256 to be compared.
843 *
844 * Returns: %TRUE if the decimal isn't equal to the other decimal,
845 * %FALSE otherwise.
846 *
847 * Since: 3.0.0
848 */
849 gboolean
garrow_decimal256_not_equal(GArrowDecimal256 * decimal,GArrowDecimal256 * other_decimal)850 garrow_decimal256_not_equal(GArrowDecimal256 *decimal,
851 GArrowDecimal256 *other_decimal)
852 {
853 return garrow_decimal_not_equal<arrow::Decimal256>(decimal, other_decimal);
854 }
855
856 /**
857 * garrow_decimal256_less_than:
858 * @decimal: A #GArrowDecimal256.
859 * @other_decimal: A #GArrowDecimal256 to be compared.
860 *
861 * Returns: %TRUE if the decimal is less than the other decimal,
862 * %FALSE otherwise.
863 *
864 * Since: 3.0.0
865 */
866 gboolean
garrow_decimal256_less_than(GArrowDecimal256 * decimal,GArrowDecimal256 * other_decimal)867 garrow_decimal256_less_than(GArrowDecimal256 *decimal,
868 GArrowDecimal256 *other_decimal)
869 {
870 return garrow_decimal_less_than<arrow::Decimal256>(decimal, other_decimal);
871 }
872
873 /**
874 * garrow_decimal256_less_than_or_equal:
875 * @decimal: A #GArrowDecimal256.
876 * @other_decimal: A #GArrowDecimal256 to be compared.
877 *
878 * Returns: %TRUE if the decimal is less than the other decimal
879 * or equal to the other decimal, %FALSE otherwise.
880 *
881 * Since: 3.0.0
882 */
883 gboolean
garrow_decimal256_less_than_or_equal(GArrowDecimal256 * decimal,GArrowDecimal256 * other_decimal)884 garrow_decimal256_less_than_or_equal(GArrowDecimal256 *decimal,
885 GArrowDecimal256 *other_decimal)
886 {
887 return garrow_decimal_less_than_or_equal<arrow::Decimal256>(decimal, other_decimal);
888 }
889
890 /**
891 * garrow_decimal256_greater_than:
892 * @decimal: A #GArrowDecimal256.
893 * @other_decimal: A #GArrowDecimal256 to be compared.
894 *
895 * Returns: %TRUE if the decimal is greater than the other decimal,
896 * %FALSE otherwise.
897 *
898 * Since: 3.0.0
899 */
900 gboolean
garrow_decimal256_greater_than(GArrowDecimal256 * decimal,GArrowDecimal256 * other_decimal)901 garrow_decimal256_greater_than(GArrowDecimal256 *decimal,
902 GArrowDecimal256 *other_decimal)
903 {
904 return garrow_decimal_greater_than<arrow::Decimal256>(decimal, other_decimal);
905 }
906
907 /**
908 * garrow_decimal256_greater_than_or_equal:
909 * @decimal: A #GArrowDecimal256.
910 * @other_decimal: A #GArrowDecimal256 to be compared.
911 *
912 * Returns: %TRUE if the decimal is greater than the other decimal
913 * or equal to the other decimal, %FALSE otherwise.
914 *
915 * Since: 3.0.0
916 */
917 gboolean
garrow_decimal256_greater_than_or_equal(GArrowDecimal256 * decimal,GArrowDecimal256 * other_decimal)918 garrow_decimal256_greater_than_or_equal(GArrowDecimal256 *decimal,
919 GArrowDecimal256 *other_decimal)
920 {
921 return garrow_decimal_greater_than_or_equal<arrow::Decimal256>(decimal, other_decimal);
922 }
923
924 /**
925 * garrow_decimal256_to_string_scale:
926 * @decimal: A #GArrowDecimal256.
927 * @scale: The scale of the decimal.
928 *
929 * Returns: The string representation of the decimal.
930 *
931 * It should be freed with g_free() when no longer needed.
932 *
933 * Since: 3.0.0
934 */
935 gchar *
garrow_decimal256_to_string_scale(GArrowDecimal256 * decimal,gint32 scale)936 garrow_decimal256_to_string_scale(GArrowDecimal256 *decimal, gint32 scale)
937 {
938 return garrow_decimal_to_string_scale<arrow::Decimal256>(decimal, scale);
939 }
940
941 /**
942 * garrow_decimal256_to_string:
943 * @decimal: A #GArrowDecimal256.
944 *
945 * Returns: The string representation of the decimal.
946 *
947 * It should be freed with g_free() when no longer needed.
948 *
949 * Since: 3.0.0
950 */
951 gchar *
garrow_decimal256_to_string(GArrowDecimal256 * decimal)952 garrow_decimal256_to_string(GArrowDecimal256 *decimal)
953 {
954 return garrow_decimal_to_string<arrow::Decimal256>(decimal);
955 }
956
957 /**
958 * garrow_decimal256_to_bytes:
959 * @decimal: A #GArrowDecimal256.
960 *
961 * Returns: (transfer full): The binary representation of the decimal.
962 *
963 * Since: 3.0.0
964 */
965 GBytes *
garrow_decimal256_to_bytes(GArrowDecimal256 * decimal)966 garrow_decimal256_to_bytes(GArrowDecimal256 *decimal)
967 {
968 return garrow_decimal_to_bytes<arrow::Decimal256>(decimal);
969 }
970
971 /**
972 * garrow_decimal256_abs:
973 * @decimal: A #GArrowDecimal256.
974 *
975 * Computes the absolute value of the @decimal destructively.
976 *
977 * Since: 3.0.0
978 */
979 void
garrow_decimal256_abs(GArrowDecimal256 * decimal)980 garrow_decimal256_abs(GArrowDecimal256 *decimal)
981 {
982 garrow_decimal_abs<arrow::Decimal256>(decimal);
983 }
984
985 /**
986 * garrow_decimal256_negate:
987 * @decimal: A #GArrowDecimal256.
988 *
989 * Negate the current value of the @decimal destructively.
990 *
991 * Since: 3.0.0
992 */
993 void
garrow_decimal256_negate(GArrowDecimal256 * decimal)994 garrow_decimal256_negate(GArrowDecimal256 *decimal)
995 {
996 garrow_decimal_negate<arrow::Decimal256>(decimal);
997 }
998
999 /**
1000 * garrow_decimal256_plus:
1001 * @left: A #GArrowDecimal256.
1002 * @right: A #GArrowDecimal256.
1003 *
1004 * Returns: (transfer full): The added value of these decimals.
1005 *
1006 * Since: 3.0.0
1007 */
1008 GArrowDecimal256 *
garrow_decimal256_plus(GArrowDecimal256 * left,GArrowDecimal256 * right)1009 garrow_decimal256_plus(GArrowDecimal256 *left,
1010 GArrowDecimal256 *right)
1011 {
1012 return garrow_decimal_plus<arrow::Decimal256>(left, right);
1013 }
1014
1015 /**
1016 * garrow_decimal256_multiply:
1017 * @left: A #GArrowDecimal256.
1018 * @right: A #GArrowDecimal256.
1019 *
1020 * Returns: (transfer full): The multiplied value of these decimals.
1021 *
1022 * Since: 3.0.0
1023 */
1024 GArrowDecimal256 *
garrow_decimal256_multiply(GArrowDecimal256 * left,GArrowDecimal256 * right)1025 garrow_decimal256_multiply(GArrowDecimal256 *left,
1026 GArrowDecimal256 *right)
1027 {
1028 return garrow_decimal_multiply<arrow::Decimal256>(left, right);
1029 }
1030
1031 /**
1032 * garrow_decimal256_divide:
1033 * @left: A #GArrowDecimal256.
1034 * @right: A #GArrowDecimal256.
1035 * @remainder: (out) (nullable): A return location for the remainder
1036 * value of these decimals. The returned #GArrowDecimal256 be
1037 * unreferred with g_object_unref() when no longer needed.
1038 * @error: (nullable): Return location for a #GError or %NULL.
1039 *
1040 * Returns: (nullable) (transfer full): The divided value of
1041 * these decimals or %NULL on error.
1042 *
1043 * Since: 3.0.0
1044 */
1045 GArrowDecimal256 *
garrow_decimal256_divide(GArrowDecimal256 * left,GArrowDecimal256 * right,GArrowDecimal256 ** remainder,GError ** error)1046 garrow_decimal256_divide(GArrowDecimal256 *left,
1047 GArrowDecimal256 *right,
1048 GArrowDecimal256 **remainder,
1049 GError **error)
1050 {
1051 return garrow_decimal_divide<arrow::Decimal256>(left,
1052 right,
1053 remainder,
1054 error,
1055 "[decimal256][divide]");
1056 }
1057
1058 /**
1059 * garrow_decimal256_rescale:
1060 * @decimal: A #GArrowDecimal256.
1061 * @original_scale: A scale to be converted from.
1062 * @new_scale: A scale to be converted to.
1063 * @error: (nullable): Return location for a #GError or %NULL.
1064 *
1065 * Returns: (nullable) (transfer full): The rescaled decimal or %NULL on error.
1066 *
1067 * Since: 3.0.0
1068 */
1069 GArrowDecimal256 *
garrow_decimal256_rescale(GArrowDecimal256 * decimal,gint32 original_scale,gint32 new_scale,GError ** error)1070 garrow_decimal256_rescale(GArrowDecimal256 *decimal,
1071 gint32 original_scale,
1072 gint32 new_scale,
1073 GError **error)
1074 {
1075 return garrow_decimal_rescale<arrow::Decimal256>(decimal,
1076 original_scale,
1077 new_scale,
1078 error,
1079 "[decimal256][rescale]");
1080 }
1081
1082
1083 G_END_DECLS
1084
1085 GArrowDecimal128 *
garrow_decimal128_new_raw(std::shared_ptr<arrow::Decimal128> * arrow_decimal128)1086 garrow_decimal128_new_raw(std::shared_ptr<arrow::Decimal128> *arrow_decimal128)
1087 {
1088 auto decimal128 = g_object_new(garrow_decimal128_get_type(),
1089 "decimal128", arrow_decimal128,
1090 NULL);
1091 return GARROW_DECIMAL128(decimal128);
1092 }
1093
1094 std::shared_ptr<arrow::Decimal128>
garrow_decimal128_get_raw(GArrowDecimal128 * decimal128)1095 garrow_decimal128_get_raw(GArrowDecimal128 *decimal128)
1096 {
1097 auto priv = GARROW_DECIMAL128_GET_PRIVATE(decimal128);
1098 return priv->decimal128;
1099 }
1100
1101 GArrowDecimal256 *
garrow_decimal256_new_raw(std::shared_ptr<arrow::Decimal256> * arrow_decimal256)1102 garrow_decimal256_new_raw(std::shared_ptr<arrow::Decimal256> *arrow_decimal256)
1103 {
1104 auto decimal256 = g_object_new(garrow_decimal256_get_type(),
1105 "decimal256", arrow_decimal256,
1106 NULL);
1107 return GARROW_DECIMAL256(decimal256);
1108 }
1109
1110 std::shared_ptr<arrow::Decimal256>
garrow_decimal256_get_raw(GArrowDecimal256 * decimal256)1111 garrow_decimal256_get_raw(GArrowDecimal256 *decimal256)
1112 {
1113 auto priv = GARROW_DECIMAL256_GET_PRIVATE(decimal256);
1114 return priv->decimal256;
1115 }
1116