啊,BCD。如果您在 6502 装配中使用它,请鸣喇叭。
当然,最好的办法是让 COBOL MOVE 为您完成这项工作!这些可能性之一可能会有所帮助。
(可能性#1)假设您确实可以访问大型机和源代码,并且输出文件仅供您使用,请修改程序,使其仅将值移动到普通解压缩的 PIC S9(7)V99 .
(可能性 #2)假设它不是那么容易(例如,文件是其他 pgms 的输入,或者无法更改代码),您可以在系统上编写另一个 COBOL 程序来读取该文件并写入另一个文件。将带有 BCD 的文件记录布局剪切并粘贴到用于输入和输出文件的新程序中。将输出版本修改为非打包。读取一条记录,执行“移动对应”以传输数据,然后写入,直到 eof。然后传输那个文件。
(可能性#3)如果您无法触摸大型机,请注意您在评论中链接的文章中的描述。 BCD相对简单。 可能就这么简单(vb.net):
Private Function FromBCD(ByVal BCD As String, ByVal intsz As Integer, ByVal decsz As Integer) As Decimal
Dim PicLen As Integer = intsz + decsz
Dim result As Decimal = 0
Dim val As Integer = Asc(Mid(BCD, 1, 1))
Do While PicLen > 0
result *= 10D
result += val \ 16
PicLen -= 1
If PicLen > 0 Then
result *= 10D
result += val Mod 16
PicLen -= 1
BCD = Mid(BCD, 2)
End If
val = Asc(Mid(BCD, 1, 1))
Loop
If val Mod 16 = &HD& Then
result = -result
End If
Return result / CDec(10 ^ decsz)
End Function
我用这个调用的一些变体对其进行了测试:
MsgBox(FromBCD("@" & Chr(13 + 16), 2, 1))
例如,是 -40.1。但只有少数。所以它可能仍然是错误的。
那么如果你的 comp-3 从输入记录布局的第 10 个字节开始,这将解决它:
dim valu as Decimal = FromBCD(Mid(InputLine,10,5), 7,2))
注意数据转换文章中用于发送字节数的公式,以及 V 之前和之后的 9 数。
将结果存储在小数中以避免舍入错误。特别是如果是$$$。 Float & Double 会让你伤心!如果你不处理它,即使是一个字符串也更好。
当然可能会更难。在我工作的地方,大型机是每字节 9 位。严肃的。这就是使前两种可能性如此突出的原因。当然,真正让他们变得更好的是,您可能只是一名 PC 程序员,这是让大型机程序员为您完成工作的一个很好的借口!如果你有幸拥有这样的选择......
和平,
-铝