Este tópico descreve os conceitos, as considerações, os casos de uso e os exemplos do tipo de dados DECIMAL no MaxCompute.
Visão geral
O DECIMAL é um tipo de dados projetado para aritmética decimal de alta precisão, amplamente utilizado em cenários de computação financeira e científica que exigem rigor na exatidão dos valores. No MaxCompute, o comportamento do tipo DECIMAL varia conforme a edição de tipos de dados do projeto:
-
Tipo de dados DECIMAL 2.0 desativado
O tipo DECIMAL utiliza um formato de precisão fixa com padrão
DECIMAL(54,18). Não é possível especificar a precisão (número máximo de dígitos) nem a escala (número de casas decimais). Faixa da parte inteira: -1036+1 a 1036-1. Parte decimal: precisão de até 10-18. Para utilizar esse tipo de dados, defina a seguinte flag:SET odps.sql.decimal.odps2=false; -
Tipo de dados DECIMAL 2.0 ativado
O padrão é
DECIMAL(38,18). É possível especificar a precisão (número máximo de dígitos) e a escala (número de casas decimais). De acordo com os requisitos de precisão, duas categorias estão disponíveis:-
DECIMAL padrão: a faixa de precisão é [1,38] e a de escala é [0, precisão]. Para usar esse tipo de dados, defina as seguintes flags:
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true;Limites de escala:
-
Se
odps.sql.decimal2.extended.scale.enable=false(padrão):A faixa de escala suportada é
[0, 18]. Todos os resultados de computação são truncados em 18 casas decimais. -
Caso
odps.sql.decimal2.extended.scale.enable=true:Há suporte para computação de alta precisão com faixa de escala de
[0, 38]. -
Ao definir
odps.sql.decimal256.auto.promotion=true;para ativar a promoção automática de tipo:O sistema promove automaticamente os resultados da computação para o tipo DECIMAL256 de maior precisão conforme necessário, abrangendo uma gama mais ampla de cálculos de alta exatidão.
-
-
DECIMAL256: a faixa de precisão é [39,76] e a de escala é [0, precisão]. Para utilizar esse tipo de dados, defina as seguintes flags:
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; SET odps.sql.decimal256.enable=true;
-
Ao ativar odps.sql.decimal256.enable=true, também é obrigatório definir odps.sql.type.system.odps2 e odps.sql.decimal.odps2 como true. Caso contrário, as consultas retornarão um erro.
Considerações
Uma única tabela não pode conter simultaneamente os tipos de dados DECIMAL antigo e novo.
Com o tipo de dados DECIMAL 2.0 ativado, se o modo compatível com Hive estiver habilitado (
SET odps.sql.hive.compatible=true;) ou o modo compatível com BigQuery estiver ativo (SET odps.sql.bigquery.compatible=true;), os valoresDECIMAL(precision, scale)serão arredondados durante a importação de dados (Tunnel Upload) e nas computações SQL caso o número de casas decimais exceda a escala definida. Se a parte inteira ultrapassar o limite, nenhum erro será retornado, mas os dados de entrada tornar-se-ão NULL.Ao definir
odps.sql.decimal.tostring.trimzerocomotrue, os zeros à direita após o ponto decimal são removidos. Quando configurado comofalse, esses zeros são preservados. Essa regra aplica-se apenas a valores lidos de tabelas, não afetando valores estáticos. Padrão:true.
Casos de uso
|
Tipo de dados |
Configuração |
Descrição |
|
DECIMAL legado |
|
Tipo de dados DECIMAL 2.0 desativado. Não é possível especificar precisão e escala. Padrão: |
|
DECIMAL padrão |
|
Tipo DECIMAL padrão com precisão de até 38. Durante a computação, a escala limita-se a 18. |
|
|
Tipo DECIMAL padrão com precisão de até 38. Suporta computação de alta precisão com faixa de escala de |
|
|
DECIMAL256 |
|
Ativa o DECIMAL256, mas mantém o comportamento original quando a precisão dos valores DECIMAL envolvidos nas computações é igual ou inferior a 38. Ideal para atualizar do DECIMAL padrão (faixa de escala |
|
|
Ativa o DECIMAL256, preservando o comportamento original quando a precisão dos valores DECIMAL nas computações for de 38 ou menos. Recomendado para migrar do DECIMAL padrão (faixa de escala |
|
|
|
Ativa o DECIMAL256 com todas as capacidades. Mais indicado para novos projetos sem requisitos de compatibilidade com versões anteriores. |
Exemplos
Tipo de dados DECIMAL 2.0 desativado
Exemplo 1: O tipo DECIMAL assume o padrão DECIMAL(54,18) e não permite ajustes.
-- Disable the DECIMAL 2.0 data type.
SET odps.sql.decimal.odps2=false;
-- Column a is of the DECIMAL type with fixed precision/scale (54,18). Adjustment is not supported.
CREATE OR REPLACE TABLE foo_t(a DECIMAL);
-- The following CREATE statement returns an error because specifying precision/scale is not supported in this mode.
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
Tipo de dados DECIMAL 2.0 ativado
-
Exemplo 1: O tipo DECIMAL permite especificar precisão e escala.
-- Enable the DECIMAL 2.0 data type. SET odps.sql.decimal.odps2=true; CREATE OR REPLACE TABLE foo_t(a DECIMAL(4,2)); -
Exemplo 2: Quando não se especificam precisão e escala para o tipo DECIMAL, o valor padrão depende da ativação do modo compatível com Hive. Com esse modo desativado, o padrão é DECIMAL(38,18). Já com o modo compatível com Hive habilitado, o padrão torna-se DECIMAL(10,0).
-- Enable the DECIMAL 2.0 data type with Hive-compatible mode disabled. SET odps.sql.decimal.odps2=true; SET odps.sql.hive.compatible=false; CREATE OR REPLACE TABLE foo_t(a DECIMAL); -- The data type of column a is 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) | | | +------------------------------------------------------------------------------------+ -- Enable the DECIMAL 2.0 data type with Hive-compatible mode enabled. SET odps.sql.decimal.odps2=true; SET odps.sql.hive.compatible=true; CREATE OR REPLACE TABLE foo_t(a DECIMAL); -- The data type of column a is 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) | | | +------------------------------------------------------------------------------------+ -
Exemplo 3: No DECIMAL padrão, a precisão varia de [1,38] e a escala de [0, precisão]. Para habilitar computação de alta precisão com escala entre [0,38], execute
SET odps.sql.decimal2.extended.scale.enable=true;.SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; -- Enable the DECIMAL 2.0 data type. SET odps.sql.decimal2.extended.scale.enable=true; -- Enable high-precision computation with a scale range of [0,38]. -- Multiply two DECIMAL values. The result data type is 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 -- Set the flag to false. The output type scale is truncated to 18, resulting in decimal(22,18). SET odps.sql.decimal2.extended.scale.enable=false; -- Disable extended scale. Scale range: [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 -
Exemplo 4: Para o DECIMAL256, a faixa de precisão é [39,76] e a de escala é [0, precisão].
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 -
Exemplo 5: Ao multiplicar dois valores DECIMAL padrão, o resultado será, por padrão, do tipo DECIMAL padrão. Caso o resultado exceda a faixa permitida, ele será truncado.
SET odps.sql.type.system.odps2=true; SET odps.sql.decimal.odps2=true; -- The result type is decimal(38,5) because it is truncated to fit the standard DECIMAL range. 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.0Quando o
DECIMAL256está ativado e se defineSET odps.sql.decimal256.auto.promotion=true;para permitir a promoção automática de tipos, o sistema eleva automaticamente os resultados das computações para tiposDECIMAL256de maior precisão. Isso evita truncamentos e preserva a exatidão total dos valores.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; -- The result type is decimal(61,5). The product of two standard DECIMAL values is promoted to the DECIMAL256 range. 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