gpt4 book ai didi

java - 如何将数据转换为压缩十进制格式

转载 作者:行者123 更新时间:2023-12-02 09:47:23 27 4
gpt4 key购买 nike

我正在尝试将 float 转换为压缩十进制,但我找到的最接近的解决方案是 Gilbert Le Blanc 的这篇文章: Java: Convert String to packed decimal

这个解决方案被复制粘贴了数百次,导致堆栈溢出,但它存在严重缺陷:

public class PackedDecimal {

public static byte[] format(long number, int bytes) {
byte[] b = new byte[bytes];

final byte minusSign = 0x0D; // Minus
final byte noSign = 0x0F; // Unsigned

String s = Long.toString(number);
int length = s.length();
boolean isNegative = false;

if (s.charAt(0) == '-') {
isNegative = true;
s = s.substring(1);
length--;
}

int extraBytes = length - bytes + 1;

if (extraBytes < 0) {
// Pad extra byte positions with zero
for (int i = 0; i < -extraBytes; i++) {
b[i] = 0x00;
}
} else if (extraBytes > 0) {
// Truncate the high order digits of the number to fit
s = s.substring(extraBytes);
length -= extraBytes;
extraBytes = 0;
}

// Translate the string digits into bytes
for (int i = 0; i < length; i++) {
String digit = s.substring(i, i + 1);
b[i - extraBytes] = Byte.valueOf(digit);
}

// Add the sign byte
if (isNegative) {
b[bytes - 1] = minusSign;
} else {
b[bytes - 1] = noSign;
}

return b;
}

public static void main(String[] args) {
long number = -456L;
byte[] b = PackedDecimal.format(number, 5);
System.out.println("Number: " + number + ", packed: " + byteToString(b));

number = 0L;
b = PackedDecimal.format(number, 5);
System.out.println("Number: " + number + ", packed: " + byteToString(b));

number = 5823L;
b = PackedDecimal.format(number, 5);
System.out.println("Number: " + number + ", packed: " + byteToString(b));

number = 123456L;
b = PackedDecimal.format(number, 5);
System.out.println("Number: " + number + ", packed: " + byteToString(b));
}

public static String byteToString(byte[] b) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < b.length; i++) {
sb.append("0x");
sb.append(Integer.toHexString((int) b[i]).toUpperCase());
sb.append(" ");
}
return sb.toString();
}

}

这是测试结果。

Number: -456, packed: 0x0 0x4 0x5 0x6 0xD 
Number: 0, packed: 0x0 0x0 0x0 0x0 0xF
Number: 5823, packed: 0x5 0x8 0x2 0x3 0xF
Number: 123456, packed: 0x3 0x4 0x5 0x6 0xF

这段代码的问题是:

  1. 它仅处理 int。 double 和 bigdecimal 也可以转换为压缩十进制。
  2. 每个数字由半个字节表示,因此压缩十进制的位数必须始终是偶数而不是奇数。
  3. 据我所知,在 COBOL 运行的应用程序中,通常每个要转换的数据字段都有一个长度变量,以及转换的数据数量的长度小数点后的数字。对于每个压缩十进制数,代码的固定长度为 5。

The number of half bytes used in packed decimal is calculated as length + 1 + (1 if the total number of half bytes is odd)

这段代码忽略了所有这些。

以下是压缩十进制转换的一些示例(l=长度,使用的一半字节)(p=小数点后使用的一半字节数):

(l=4)(p=0) +123 > 00123C (l=4)(p=0)-123 > 00123D 
(l=4)(p=0)(Unsigned) 12345 > 12345F
(l=6)(p=2)(Unsigned) 12345.67 > 1234567F
(l=8)(p=2)(Unsigned) 12345.67 > 001234567F
(l=6)(p=3)(Unsigned) > 12345.67 > 2345670F

关于如何改进它有什么建议吗?

最佳答案

有一些库可以实现这一点。例如。你可以使用 JTOpen来自 IBM 的 AS400 兼容性。 blog post by Michael Wan 中描述了它用于将 Java BigDecimal 转换为压缩十进制并返回的用法。 - 引用:

/**
* Java BigDecimal to Packed Decimal
*/
//15 means total number of digits, 5 means number of decimal places
AS400PackedDecimal packedDecimal = new AS400PackedDecimal(15, 5);
BigDecimal javaBigDecimal = new BigDecimal("1000.12345");
byte[] convertedBytesArray = packedDecimal.toBytes(javaBigDecimal);

/**
* Packed Decimal to Java Big Decimal
*/
BigDecimal convertedBigDecimal = (BigDecimal)packedDecimal.toObject(convertedBytesArray);

其他我不知道的库:

关于java - 如何将数据转换为压缩十进制格式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56545971/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com