數據類型表:
類型縮寫 | 類型 | 默認長度 | 允許長度 | 初始值 | 描述 |
C | 文本型 | 1 | ? | Space | 字符串數據,如'Program' |
D | 日期型 | 8 | 8 | '00000000' | 日期數據,格式為YYYYMMDD |
F | 浮點型 | 8 | 8 | 0 | 浮點數 |
I | 整型 | 4 | 10 | 0 | 帶正負符號的整數 |
N | 數值型 | 1 | 31 | '00…0' | 數值所組成的字符串 |
P | 壓縮型 | 8 | 16 | 0 | 將兩個 十進制數字壓縮到一個字節 |
T | 時間型 | 6 | 6 | '000000' | 時間 |
?
P類型(壓縮型)數據
是一種壓縮的定點數,其數據對象占據內存字節數和數值范圍取定義時指定的整個數據大小和小數點后位數,如果不指定小數位,則將視為I類型。其有效數字位大小可以是從1~31位數字(小數點與正負號占用一個位置,半個字節),小數點后最多允許14個數字。
P類型的數據,可用于精確運算(這里的精確指的是存儲中所存儲的數據與定義時字面上所看到的大小相同,而不存在精度丟失問題——看到的就是內存中實實在在的大小)。在使用P類型時,要先選擇程序屬性中的選項 Fixed point arithmetic(即定點算法,一般默認選中),否則系統將P類型看用整型。其效率低于I或F類型。
"16 * 2 = 32表示了整個字面意義上允許的最大字面個數,而14表示的是字面上小數點后面允許的最大小數位,而不是指14個字節,只有這里定義時的16才表示16個字節
DATA: p(16) TYPE p DECIMALS 14 VALUE '12345678901234567.89012345678901'.
"正負符號與小數點固定要占用半個字節,一個字面上位置,并包括在這16個字節里面。 "16 * 2 = 32位包括了小數點與在正負號在內 "在定義時字面上允許最長可以達到32位,除去小數點與符號需占半個字節以后 "有效數字位可允許31位,這31位中包括了整數位與小數位,再除去定義時小 "數位為14位外,整數位最多還可達到17位,所以下面最多只能是17個9 DATA: p1(16) TYPE p DECIMALS 14 VALUE '-99999999999999999'.
"P類型是以字符串來表示一個數的,與字符串不一樣的是,P類型中的每個數字位只會占用4Bit位,所以兩個數字位才會占用一個字節。另外,如果定義時沒有指定小數位,表示是整型,但小數點固定要占用半個字節,所以不帶小數位與符號的最大與最小整數如下(最多允許31個9,而不是32個) DATA: p1(16) TYPE p? VALUE '+9999999999999999999999999999999'. DATA: p2(16) TYPE p? VALUE '-9999999999999999999999999999999'.
其實P類型是以字符串形式來表示一個小數,這樣才可以作到精確,就像Java中要表示一個精確的小數要使用BigDecimal一樣,否則會丟失精度。
DATA: p(9) TYPE p DECIMALS 2 VALUE '-123456789012345.12'. WRITE: / p."123456789012345.12-
DATA: f1 TYPE f VALUE '2.0', ????? f2 TYPE f VALUE '1.1', ????? f3 TYPE f. f3? =? f1 - f2."不能精確計算 "2.0000000000000000E+00 1.1000000000000001E+00 8.9999999999999991E-01 WRITE: / f1?? , f2 , f3.
DATA: p1 TYPE p DECIMALS 1 VALUE '2.0', ????? p2 TYPE p DECIMALS 1 VALUE '1.1', ????? p3 TYPE p DECIMALS 1. p3? =? p1 - p2."能精確計算 WRITE: / p1?? , p2 , p3. "2.0?????????????? 1.1?????????????? 0.9
Java中精確計算:
??? publicstaticvoid main(String[] args) {
??????? System.out.println(2.0 - 1.1);// 0.8999999999999999
??????? System.out.println(sub(2.0, 0.1));// 1.9
??? }
??? publicstaticdouble sub(double v1, double v2) {
??????? BigDecimal b1 = new BigDecimal(Double.toString(v1));
??????? BigDecimal b2 = new BigDecimal(Double.toString(v2));
??????? return b1.subtract(b2).doubleValue();
??? }