SQL Server、Oracle、PostgreSQL における小数を含む数値型の違い
案件の中で「小数を含む数値型の仕様」を知らずに困った経験があり、備忘録としてまとめます。
特にDECIMAL / NUMERIC / NUMBER 型の「精度 (precision=p)」「スケール (scale=s)」指定の違いを中心に整理しました。
1. 各DBの代表的な「小数あり数値型」
| データベース | 代表的な型 | 備考 |
|---|---|---|
| SQL Server |
DECIMAL, NUMERIC, FLOAT, REAL
|
DECIMALとNUMERICは同義 |
| Oracle |
NUMBER, BINARY_FLOAT, BINARY_DOUBLE
|
NUMBERが最も汎用的 |
| PostgreSQL |
NUMERIC, DECIMAL, REAL, DOUBLE PRECISION
|
NUMERICとDECIMALは同義 |
本記事では、特にNUMERIC / NUMBER など「精度指定が可能な型」中心に説明します。
2️. p(精度)と s(スケール)の意味
- 精度 (p): 有効桁数の最大値
- スケール (s): 小数点以下の桁数
例:NUMERIC(5, 2)
- 最大5桁、うち小数2桁(→例: 999.99)
3️. スケールに「負の数」を指定できるか
小数型定義の重要な違いは「スケール(s)に負の数を指定できるか」です。
SQL Server
-
NUMERIC(p, s)は s=0~p の範囲で指定。 - 負のスケールは不可。
- 小数点より左側の桁で四捨五入したい場合は
ROUND()関数を使う。
Oracle
-
NUMBER(p, s)は 負のスケールを指定可能。 - sが負の場合 → 整数部を四捨五入する。
例:
-
NUMBER(5, -2)→ 整数部の2桁目を四捨五入にする-
12345→12300 -
12367→12400 -
123.45→100
-
PostgreSQL
-
NUMERIC(p, s)は s=0以上のみ指定可。 - 負のスケールは不可。
- 整数部を四捨五入したい場合も
ROUND()など関数で処理。
ただし、上記はPostgreSQL 15以降では負のスケールを指定できる。
4️. デフォルトの挙動の違い
pとsを指定しなかった場合の挙動の違いについて
SQL Server
-
NUMERICのデフォルト →(18, 0) - 指定なしだと整数18桁まで。
Oracle
-
NUMBERは精度・スケールを省略可能。 - 挿入値に応じて 最大38桁の有効桁数 を柔軟に保持する。
PostgreSQL
-
NUMERICで精度・スケールを省略可能 - 柔軟に(挿入値に応じて)最大の精度を保持。
5. 型ごとの値の範囲
SQL Server
-
NUMERIC- p=1〜38 桁
- s=0~p 桁
Oracle
-
NUMBER- p=1〜38 桁
- s=-84〜127 桁
PostgreSQL
-
NUMERIC- p=1~1000 桁
- s=0~p 桁(PostgreSQL 14まで)
- s=-1000~1000 桁(PostgreSQL 15以降)
6. まとめ比較表
| 特徴 | SQL Server | Oracle | PostgreSQL |
|---|---|---|---|
| 負のスケール | ❌ 不可 | ✅ 可能 | ✅ 可能(PostgreSQL 15以降。14まで不可) |
| デフォルト | (18, 0) |
挿入値に応じて柔軟 | 挿入値に応じて柔軟 |
| 最大精度 | 38桁まで | 38桁(ただしスケール指定範囲は広い) | ほぼ制限なし(システム依存) |
7. 結論
- SQL Server は、負のスケール指定不可。
- Oracle は、負のスケール指定による整数部を四捨五入することができる。
- PostgreSQL は、v15以降で負のスケール指定が可能になり、非常に大きな桁数を正確に格納できる。