1

将字母数字移动到数字变量会导致意外结果。这是代码:

  DATA DIVISION.                                 
  WORKING-STORAGE SECTION.                       
  01  WS-VAR-STR       PIC X(3) VALUE SPACES.                
  01  WS-VAR-NUM       PIC 9(3) VALUE ZEROES. 
  PROCEDURE DIVISION.                            
      MOVE '1'         TO WS-VAR-STR                  
      MOVE WS-VAR-STR  TO WS-VAR-NUM
      DISPLAY 'STRING > ' WS-VAR-STR '< MOVED > ' WS-VAR-NUM '<'

      IF WS-VAR-NUM >= 40 AND <= 59
         DISPLAY 'INSIDE IF >' WS-VAR-NUM
      ELSE 
         DISPLAY 'INSIDE ELSE >' WS-VAR-NUM
      END-IF
      GOBACK                                     
      .  

    OUTPUT:
    STRING > 1  < MOVED > 1 0<
    INSIDE ELSE >1 O

结果很奇怪,想弄清楚为什么将“1”作为“1 0”移动到数字变量中,有趣的是,调节它也没有问题。分享你的观点。感谢您的关注。

4

1 回答 1

3

基本上你已经做了非法的MOVE。如果字母数字字段的内容仅包含数字字符,则将字母数字字段移动到数字字段是有效的。该参考 总结了有效/无效的移动。

你期待的结果是什么?

字母数字字段到数字字段的移动无需“转换”即可完成。基本上,您只需将一个数字后跟两个空格放入数字字段中。'1' 没问题,两个空格不行。最后两个字节WS-VAR-NUM包含空格。

但是等等……为什么最后一个字符是零?这个问题的答案有点复杂。声明为PIC 9某物的项目以分区十进制表示。分区十进制数的每个数字都由一个字节表示。每个字节的高4位为区位;低位字节的高 4 位代表项目的符号。每个字节的 4 个低位包含数字的值。这里的关键是符号的存储位置。它位于最后一个字节的高位。你的声明没有包括一个标志,所以MOVE语句清除符号位并用默认的数字高位替换它们(记住 MOVE 的唯一有效字符是数字 - 所以这个补丁过程应该总是产生一个有效的结果)。无符号分区十进制数字的高位总是 HEX F。最后一个字节的低位是什么?空格的 ebcdic HEX 值为 40。零是 HEX F0。由于 MOVE 语句会自动“修复”符号,因此您最终会在低位数字中得到 HEX F0,您猜对了,它恰好是零。其他“数字”都不包含符号位,因此它们保持原样。

最后,一条DISPLAY语句将分区十进制字段转换为它们的等效字符表示形式以供表示:净结果为:'1 0'。

顺便说一句,上面的讨论是它在 IBM z/OS 平台上的工作方式——其他字符集(例如 ASCII)和/或其他平台可能会产生不同的结果,不是因为 IBM 做错了事情,而是因为程序正在做一个非法MOVE的,结果基本上是未定义的。

于 2011-05-26T20:20:49.313 回答