Topik ini menjelaskan konsep, pertimbangan, kasus penggunaan, dan contoh tipe data DECIMAL di MaxCompute.
Ikhtisar
DECIMAL adalah tipe data yang dirancang untuk aritmetika desimal berpresisi tinggi, banyak digunakan dalam skenario komputasi ilmiah dan keuangan yang memerlukan presisi ketat. Di MaxCompute, perilaku tipe DECIMAL bervariasi tergantung pada edisi tipe data proyek:
-
Tipe data DECIMAL 2.0 dinonaktifkan
Tipe DECIMAL menggunakan format presisi tetap dengan nilai default
DECIMAL(54,18). Presisi (jumlah maksimum digit) dan skala (jumlah tempat desimal) tidak dapat ditentukan. Rentang bagian integer: -1036+1 hingga 1036-1. Bagian desimal: akurat hingga 10-18. Untuk menggunakan tipe data ini, atur flag berikut:SET odps.sql.decimal.odps2=false; -
Tipe data DECIMAL 2.0 diaktifkan
Default menjadi
DECIMAL(38,18). Anda dapat menentukan presisi (jumlah maksimum digit) dan skala (jumlah tempat desimal). Berdasarkan kebutuhan presisi, tersedia dua kategori berikut:-
DECIMAL Standar: rentang presisi [1,38], rentang skala [0, presisi]. Untuk menggunakan tipe data ini, atur flag berikut:
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true;Batas skala:
-
Jika
odps.sql.decimal2.extended.scale.enable=false(default):Rentang skala yang didukung adalah
[0, 18]. Semua hasil komputasi dipotong menjadi 18 tempat desimal. -
Jika
odps.sql.decimal2.extended.scale.enable=true:Komputasi berpresisi tinggi dengan rentang skala
[0, 38]didukung. -
Jika
odps.sql.decimal256.auto.promotion=true;diatur untuk mengaktifkan promosi tipe otomatis:Sistem secara otomatis mempromosikan hasil komputasi ke tipe DECIMAL256 berpresisi lebih tinggi sesuai kebutuhan, mendukung rentang perhitungan berpresisi tinggi yang lebih luas.
-
-
DECIMAL256: rentang presisi [39,76], rentang skala [0, presisi]. Untuk menggunakan tipe data ini, atur flag berikut:
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; SET odps.sql.decimal256.enable=true;
-
Saat odps.sql.decimal256.enable=true diaktifkan, odps.sql.type.system.odps2 dan odps.sql.decimal.odps2 juga harus diatur ke true. Jika tidak, kueri akan mengembalikan error.
Pertimbangan
-
Satu tabel tidak dapat berisi tipe data DECIMAL lama dan baru sekaligus.
-
Dengan tipe data DECIMAL 2.0 diaktifkan, saat mode kompatibilitas Hive (
SET odps.sql.hive.compatible=true;) atau mode kompatibilitas BigQuery (SET odps.sql.bigquery.compatible=true;) diaktifkan, nilaiDECIMAL(presisi, skala)dibulatkan selama impor data (Tunnel Upload) dan komputasi SQL jika jumlah tempat desimal melebihi skala. Jika bagian integer melebihi batas, tidak ada error yang dikembalikan, tetapi data masukan menjadi NULL. -
Saat
odps.sql.decimal.tostring.trimzerodiatur ketrue, nol di akhir setelah titik desimal dihapus. Saat diatur kefalse, nol di akhir dipertahankan. Aturan ini hanya berlaku untuk nilai yang dibaca dari tabel, bukan untuk nilai statis. Default:true.
Kasus Penggunaan
|
Tipe data |
Konfigurasi |
Deskripsi |
|
Legacy DECIMAL |
|
Tipe data DECIMAL 2.0 dinonaktifkan. Presisi dan skala tidak dapat ditentukan. Default: |
|
Standard DECIMAL |
|
Tipe DECIMAL standar dengan presisi hingga 38. Selama komputasi, skala dibatasi hingga 18. |
|
|
Tipe DECIMAL standar dengan presisi hingga 38. Mendukung komputasi berpresisi tinggi dengan rentang skala |
|
|
DECIMAL256 |
|
Mengaktifkan DECIMAL256, tetapi mempertahankan perilaku asli saat presisi nilai DECIMAL yang terlibat dalam komputasi adalah 38 atau kurang. Cocok untuk meningkatkan dari DECIMAL standar (rentang skala |
|
|
Mengaktifkan DECIMAL256, tetapi mempertahankan perilaku asli saat presisi nilai DECIMAL yang terlibat dalam komputasi adalah 38 atau kurang. Cocok untuk meningkatkan dari DECIMAL standar (rentang skala |
|
|
|
Mengaktifkan DECIMAL256 dengan kemampuan penuh. Cocok untuk proyek baru yang tidak memiliki persyaratan kompatibilitas mundur. |
Contoh
Tipe data DECIMAL 2.0 dinonaktifkan
Contoh 1: Tipe DECIMAL default menjadi DECIMAL(54,18) dan tidak dapat disesuaikan.
-- Nonaktifkan tipe data DECIMAL 2.0.
SET odps.sql.decimal.odps2=false;
-- Kolom a bertipe DECIMAL dengan presisi/skala tetap (54,18). Penyesuaian tidak didukung.
CREATE OR REPLACE TABLE foo_t(a DECIMAL);
-- Pernyataan CREATE berikut mengembalikan error karena menentukan presisi/skala tidak didukung dalam mode ini.
CREATE OR REPLACE TABLE foo_t(a DECIMAL(5,2));
-- Error: FAILED: ODPS-0130071:[1,33] Semantic analysis exception - precision and scale is not currently supported in current mode, 'SET odps.sql.decimal.odps2=true' to enable
Tipe data DECIMAL 2.0 diaktifkan
-
Contoh 1: Tipe DECIMAL mendukung penentuan presisi dan skala.
-- Aktifkan tipe data DECIMAL 2.0. SET odps.sql.decimal.odps2=true; CREATE OR REPLACE TABLE foo_t(a DECIMAL(4,2)); -
Contoh 2: Saat presisi dan skala tidak ditentukan untuk tipe DECIMAL, nilai default bergantung pada status mode kompatibilitas Hive. Jika mode kompatibilitas Hive dinonaktifkan, default-nya adalah DECIMAL(38,18). Jika diaktifkan, default-nya adalah DECIMAL(10,0).
-- Aktifkan tipe data DECIMAL 2.0 dengan mode kompatibilitas Hive dinonaktifkan. SET odps.sql.decimal.odps2=true; SET odps.sql.hive.compatible=false; CREATE OR REPLACE TABLE foo_t(a DECIMAL); -- Tipe data kolom a adalah DECIMAL(38,18). DESC foo_t; -- Result: +------------------------------------------------------------------------------------+ | Owner: ALIYUN$odps_pd_testcloud_com | | Project: xxxx | | TableComment: | +------------------------------------------------------------------------------------+ | CreateTime: 2026-04-21 13:36:21 | | LastDDLTime: 2026-04-21 13:36:21 | | LastModifiedTime: 2026-04-21 13:36:21 | +------------------------------------------------------------------------------------+ | InternalTable: YES | Size: 0 | +------------------------------------------------------------------------------------+ | Native Columns: | +------------------------------------------------------------------------------------+ | Field | Type | Label | Comment | +------------------------------------------------------------------------------------+ | a | decimal(38,18) | | | +------------------------------------------------------------------------------------+ -- Aktifkan tipe data DECIMAL 2.0 dengan mode kompatibilitas Hive diaktifkan. SET odps.sql.decimal.odps2=true; SET odps.sql.hive.compatible=true; CREATE OR REPLACE TABLE foo_t(a DECIMAL); -- Tipe data kolom a adalah DECIMAL(10,0). DESC foo_t; -- Result: +------------------------------------------------------------------------------------+ | Owner: ALIYUN$odps_pd_testcloud_com | | Project: ***_project | | TableComment: | +------------------------------------------------------------------------------------+ | CreateTime: 2026-04-21 13:38:04 | | LastDDLTime: 2026-04-21 13:38:04 | | LastModifiedTime: 2026-04-21 13:38:04 | +------------------------------------------------------------------------------------+ | InternalTable: YES | Size: 0 | +------------------------------------------------------------------------------------+ | Native Columns: | +------------------------------------------------------------------------------------+ | Field | Type | Label | Comment | +------------------------------------------------------------------------------------+ | a | decimal(10,0) | | | +------------------------------------------------------------------------------------+ -
Contoh 3: Untuk DECIMAL standar, rentang presisi adalah [1,38] dan rentang skala adalah [0, presisi]. Untuk mengaktifkan komputasi berpresisi tinggi dengan rentang skala [0,38], atur
SET odps.sql.decimal2.extended.scale.enable=true;.SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; -- Aktifkan tipe data DECIMAL 2.0. SET odps.sql.decimal2.extended.scale.enable=true; -- Aktifkan komputasi berpresisi tinggi dengan rentang skala [0,38]. -- Kalikan dua nilai DECIMAL. Tipe data hasilnya adalah decimal(22,19). EXPLAIN SELECT CAST(1bd AS DECIMAL(10,9))*CAST(1bd AS DECIMAL(11,10)); -- Result: job0 is root job In Job job0: root Tasks: M1 In Task M1: VALUES: _c0 : {1} Statistics: Num rows: 1.0, Data size: 16.0 FS: output: Screen schema: _c0 (decimal(22,19)) Statistics: Num rows: 1.0, Data size: 16.0 -- Atur flag ke false. Skala tipe output dipotong menjadi 18, menghasilkan decimal(22,18). SET odps.sql.decimal2.extended.scale.enable=false; -- Nonaktifkan skala diperluas. Rentang skala: [0,18]. EXPLAIN SELECT CAST(1bd AS DECIMAL(10,9))*CAST(1bd AS DECIMAL(11,10)); -- Result: job0 is root job In Job job0: root Tasks: M1 In Task M1: VALUES: _c0 : {1} Statistics: Num rows: 1.0, Data size: 16.0 FS: output: Screen schema: _c0 (decimal(22,18)) Statistics: Num rows: 1.0, Data size: 16.0 -
Contoh 4: Untuk DECIMAL256, rentang presisi adalah [39,76] dan rentang skala adalah [0, presisi].
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; SET odps.sql.decimal256.enable=true; CREATE OR REPLACE TABLE foo_t(a decimal(60,10)); EXPLAIN SELECT * FROM foo_t; -- Result: job0 is root job In Job job0: root Tasks: M1 In Task M1: Data source: ***_project.foo_t TS: muze_project.foo_t Statistics: Num rows: 1.0, Data size: 16.0 FS: output: Screen schema: a (decimal(60,10)) Statistics: Num rows: 1.0, Data size: 16.0 -
Contoh 5: Saat dua nilai DECIMAL standar dikalikan, hasilnya adalah tipe DECIMAL standar secara default. Jika hasilnya melebihi rentang, nilai tersebut dipotong.
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; -- Tipe hasilnya adalah decimal(38,5) karena dipotong agar sesuai dengan rentang DECIMAL standar. EXPLAIN SELECT CAST(1bd AS DECIMAL(30,5)) * CAST(1bd AS DECIMAL(30,0)); -- Result: job0 is root job In Job job0: root Tasks: M1 In Task M1: VALUES: _c0 : {1} Statistics: Num rows: 1.0, Data size: 16.0 FS: output: Screen schema: _c0 (decimal(38,5)) Statistics: Num rows: 1.0, Data size: 16.0Saat
DECIMAL256diaktifkan danSET odps.sql.decimal256.auto.promotion=true;diatur untuk mengaktifkan promosi tipe otomatis, sistem secara otomatis mempromosikan hasil komputasi ke tipeDECIMAL256berpresisi lebih tinggi, sehingga menghindari pemotongan dan mempertahankan presisi penuh.SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; SET odps.sql.decimal256.enable=true; SET odps.sql.decimal256.auto.promotion=true; -- Tipe hasilnya adalah decimal(61,5). Hasil perkalian dua nilai DECIMAL standar dipromosikan ke rentang DECIMAL256. EXPLAIN SELECT CAST(1bd AS DECIMAL(30,5)) * CAST(1bd AS DECIMAL(30,0)); -- Result: job0 is root job In Job job0: root Tasks: M1 In Task M1: VALUES: _c0 : {1} Statistics: Num rows: 1.0, Data size: 16.0 FS: output: Screen schema: _c0 (decimal(61,5)) Statistics: Num rows: 1.0, Data size: 16.0