首页 > 解决方案 > MULTIPLY 的行为不像我预期的那样

问题描述

我有这个 cobol 程序,用于计算阶乘:

   IDENTIFICATION DIVISION.
   PROGRAM-ID. Factorial-hopefully.
   AUTHOR. Darth Egregious.
   DATA DIVISION.
   WORKING-STORAGE SECTION.
   01 Keeping-Track-Variables.
      05 Operand                      PIC S99   VALUE 0.
      05 Product                      PIC S99   VALUE 1.
   PROCEDURE DIVISION.
   PERFORM-FACTORIAL.
    DISPLAY SPACES
    PERFORM VARYING Operand FROM 6 BY -1 UNTIL Operand = 0

      DISPLAY "Before Product " Product " Operand " Operand
      MULTIPLY Product By Operand GIVING Product
      DISPLAY "After Product " Product " Operand " Operand
    END-PERFORM
    DISPLAY Product.
   STOP RUN.

我这样运行它:

cobc -free -x -o a.out fact.cbl && ./a.out

我得到了这个奇怪的输出:

Before Product +01 Operand +06
After Product +06 Operand +06
Before Product +06 Operand +05
After Product +30 Operand +05
Before Product +30 Operand +04
After Product +30 Operand +04
Before Product +30 Operand +03
After Product +90 Operand +03
Before Product +90 Operand +02
After Product +90 Operand +02
Before Product +90 Operand +01
After Product +90 Operand +01
+90

我的递减循环按预期工作,但MULTIPLY命令表现异常。它正在做1*6,并且6*5正确,但30*4似乎不起作用,然后起作用,30*3最后90*2又不起作用。COBOL 不喜欢乘以 2 的幂吗?

标签: cobolmultiplication

解决方案


我的递减循环按预期工作,但 MULTIPLY 命令的行为很奇怪。它正确地执行了 1*6 和 6*5,但 30*4 似乎不起作用,然后 30*3 起作用,最后 90*2 再次不起作用。COBOL 不喜欢乘以 2 的幂吗?

  05 Operand                      PIC S99   VALUE 0.
  05 Product                      PIC S99   VALUE 1.

当您乘以30*4and90*2时,值大于PICTURE子句S99.

PIC将子句的大小增加到S999.


回复评论:

从技术上讲,结果是未定义的 [ COBOL 85],因此什么都不做是一个有效的选择。其他实现将截断值给出不同的结果。

因此,与其说是语言,不如说是实现。

该语言还允许SIZE ERROR短语捕获截断错误。在这种情况下,结果不会改变,但可能会执行附加代码以指示发生了错误。

使用,如果未指定短语并且异常检查未激活COBOL 2002,则结果由实现者定义。ON SIZE ERROREC-SIZE-TRUNCATION


引用 2002 标准:

F.1 可能影响现有计划的实质性变化

15) 没有 SIZE ERROR 短语的大小错误条件。如果发生大小错误条件,发生它的语句不包含 SIZE ERROR 或 NOT SIZE ERROR 短语,并且没有相关的声明,实现者定义运行单元是否终止或继续执行以不正确的值。

理由:

在之前的 COBOL 标准中,大小错误的规则规定执行将继续使用未定义的值,但不清楚将继续执行的位置,尤其是在条件语句中。此外,对于许多关键应用程序来说,以不正确的结果继续执行是不可接受的,这可能会导致数据库损坏、程序的不正确继续执行以及潜在的大量额外错误。修改程序为每个受影响的语句添加 ON SIZE ERROR 是禁止的。响应用户要求,几个实现者在这种情况下终止了程序的执行;在某些情况下,实现者允许基于编译器指令选择终止。

在这种情况下终止的应用程序的数量和严重程度为这种变化提供了强有力的理由。预计此更改对现有程序的影响不大,因为实施者可以根据他们对先前 COBOL 标准的实施自由继续或终止。


推荐阅读