如何在cobol中显示comp变量的实际值

如何在cobol中显示comp变量的实际值,cobol,mainframe,ebcdic,Cobol,Mainframe,Ebcdic,我在COBOL程序中有以下变量,当读取该变量时,该变量从文件中获取其值: 01 Employee-number PIC 09(8) comp 01 Employee-number-x redefines Employee-number PIC x(04) 我在同一程序中有另一个变量: 01 D-element-number PIC 9(04) 现在, 将Employee number移动到D-element-number 然后我将这个D-element-number写入一个文件 从输

我在COBOL程序中有以下变量,当读取该变量时,该变量从文件中获取其值:

01 Employee-number PIC 09(8) comp
01 Employee-number-x redefines 
   Employee-number PIC x(04)
我在同一程序中有另一个变量:

01 D-element-number PIC 9(04)
现在,

Employee number
移动到
D-element-number

然后我将这个
D-element-number
写入一个文件

从输入文件读取的值为:

0013 
0024
所以这个值是
Employee number
Employee-number-x
,我将这个值移动到
D-Element-number
并将这个变量写入输出文件

但我在输出文件中得到:

4660
FFFF
4660
4660
是与
X'1234'

但我想看看这样的东西:

1234
FFFF
1234
我怎样才能做到这一点


我可以更改
D-element-number
的定义,但不能更改其他内容。

假设当你有X'0000124'时,你想要C'0000124',看看这里

暂时忽略剩下的讨论,只关注那篇文章

这是关键部分:

       PERFORM UNTIL X-WS-1000 > X-WS-1000-MAX
           MOVE WS-1000-BYTE-TBL (X-WS-1000)
                                   TO WS-PACKED-X (1:1)
           MOVE WS-PACKED          TO WS-DISPLAY
           MOVE WS-DISPLAY-X       TO WS-2000-BYTE-TBL (X-WS-2000)
           SET  X-WS-1000          UP BY 1
           SET  X-WS-2000          UP BY 1
       END-PERFORM
您需要精确的存储定义才能使用它(不要“更正”任何内容)

它的工作原理是让编译器使用“解包”指令(UNPK)。这个一次只能工作一个字节,解释起来很简单

X'12'(字节字段示例)放在一个双字节字段中。X'12ii'(其中ii的值为“无关”)

UNPK然后将此“打包”编号转换为“分区”编号。“区域”是一个字节的前四个bts,对于分区编号,四个位都设置为一。得到一个F,然后从第一个字节得到最左边的数字。然后得到第二个输出字节,前四位设置为F,然后是第二个输入位

然后,UNPK继续执行最后一个字节,该字节包含一个不相关的数字和一个不相关的符号。对于分区数字,符号和最右边的数字占用同一字节(分区中的符号),因此得到一个不相关的整字节

X'12'->X'12ii'->X'F1F1ii'

三字节输出的前两个字节是C'12'

不,对于数字来说什么都可以,但是字母会把事情弄得一团糟:

X'AB'->X'ABii'->X'FAFBii'

虽然F和a数字给出了一个可显示的数字,但对于F和字母,结果并没有直接意义

现在检查。。。转换来拯救:FA被翻译成C'A'(X'C1),字母到F也是如此

转换后的结果将是C'AB'

应该给你足够的钱去工作

还有其他方法,但这是一个与经典汇编技术相当接近的COBOL方法,具有UNPK和翻译(TR)以及翻译值表

如果你使用你最喜欢的搜索引擎。你应该能够改进更多的方法,使用计算(不止一个),查表,我甚至看到了一个256-WHEN的评估“有效”,但我猜它有点“慢”

再进一步想想,你实际上有一个BCD(二进制编码的十进制),不是吗?这是一个压缩小数,没有符号。你的领域没有阿尔法

这更容易转换

01  the-converted-value PACKED-DECIMAL PIC 9(8)V9 VALUE ZERO.
01  FILLER REDEFINES the-converted-value.
    05  the-binary-value PIC X(4).
    05  FILLER PIC X.

MOVE Employee-number-x TO the-binary-value
MOVE the-converted-value TO D-element-number (with Gilbert's correction to PIC 9(8)).
“小数位”是ii,忽略值和忽略符号。你不再需要检查。。。转换。。。因为你只有数字。如果你有BCD


回答您自己的问题的一个非常好的方法是首先找出数字是如何在二进制字段中创建的。

没有尝试此方法,但我认为它可能会起作用:

01 WN-GROUP.
   05 Employee-number PIC 9(8) comp.
   05 PACKED-ZERO     PIC 9(1) COMP-3 VALUE ZERO.

01 WN-PACKED redefines WN-GROUP PIC 9(9) COMP-3.
01 WN-UNPACKED PIC 9(9).
然后在您的程序中:

MOVE your-number TO Employee-number
MOVE WN-PACKED TO WN-UNPACKED.

最后,您可以移动或显示WN-PACKED(1:8)。

01 D-element-number PIC 9(08)或PIC 9(09)。@GilbertLeBlanc,是的,这是一个令人困惑的解释,因此可能很简单:-)@user2695332,您为什么要这样做,您能消除问题中的困惑吗。如果您正在显示的数字是“垂直十六进制”的,那么很高兴知道这一点,特别是对于00001234,您还可以显示您通常看到的“非显示”字符的“.”。您所说的“我可以更改D元素编号的定义,但不能更改任何其他内容”到底是什么意思,因为如果不编写其他代码,可能无法更改定义-然后呢?@user2695332,您在编译列表上的TRUNC选项的值是多少?如果你最好有PIC 9(9),就像TRUNC(BIN)一样,你可以得到一些9位数的数字。你的账号有多大是告诉你这个字段应该有多长的捷径。好吧,你应该试试看。例如,WN-PACKED只有五个字节长,但您建议使用八个字节。您也不能引用或修改非显示/国家字段。我的答案中包含了你想要做的,不是吗?我试过了,它很有效,只需要将WN-PACKED转换成一个未打包的变量。我正在编辑前面的代码。不管怎样,我刚刚意识到这个问题已经有一个月了。。。哈哈,也许比尔的答案是彻底改变了这一点:01 WN-PACKED重新定义了WN-GROUP PIC 9(9)COMP-3。为此:01 WN-PACKED重新定义了WN-GROUP PIC 9(8)V9 COMP-3。然后忘记参考修改。移动字段时,“小数位”将被截断。哈。刚刚注意到我的答案中有一个字段太长了…哦,是的!这样效果更好,不需要移动位置。我以前没注意到你的第一个答案基本上是,对不起。