我有一个使用如下字段的计算语句:
WS-COMPUTE PIC 9(14).
WS-NUM-1 PIC 9(09).
WS-NUM-2 PIC 9(09).
WS-NUM-3 PIC S9(11) COMP-3.
WS-DENOM PIC 9(09).
然后有逻辑来进行计算
COMPUTE WS-COMPUTE =
((WS-NUM-1 - WS-NUM-2 + WS-NUM-3)
/ WS-DENOM) * 100
因为数字<100,所以* 100在那里。期望从除法中得到1,但是0总是存储在WS-COMPUTE中。
我们通过声明另一个具有隐含小数的字段,然后将其移动到WS-COMPUTE的值来得到一个解决方法,但是我为什么原始总是用WS填充WS-COMPUTE而迷失了?
答案 0 :(得分:1)
听起来您正在使用TRUNC(STD)选项,编译器会使用picture子句来决定用于中间结果的精度。您可以在所有中间字段中添加隐含的小数,也可以尝试使用TRUNC(BIN)或TRUNC(OPT),但在这种情况下,我认为他们不会提供帮助。
截断最终的中间结果。 OS / VS COBOL具有TRUNC和NOTRUNC选项(默认为NOTRUNC)。 VS COBOL II,IBM COBOL和Enterprise COBOL具有TRUNC(STD | OPT | BIN)选项。 TRUNC(STD) 根据二进制接收字段的PICTURE规范截断数字字段 TRUNC(OPT) 以最佳方式截断数字字段 TRUNC(BIN) 根据二进制字段占用的存储空间截断二进制字段 TRUNC(STD)是默认值。
有关完整说明,请参阅“Enterprise COBOL编程指南”。
答案 1 :(得分:1)
中间计算结果的小数位数与最终结果字段中的小数位数直接相关(如果您有多个结果,可以参考手册)字段)当各个操作数中没有小数位时。对于中间结果,COBOL不会使用预定数量的小数位。如果有问题的实际操作数和最终结果都不包含小数位,则中间结果将不包含小数位。
关系是:中间结果中的小数位数=最终结果字段中的小数位数。唯一可以修改它的是ROUNDED的规范。如果指定了ROUNDED,则为中间结果字段保留一个额外的小数位,并将用于执行最终结果的舍入。
您的最终结果没有小数位,也没有ROUNDED。因此中间结果将没有小数位。如果你得到一个小于零的值,那么它就会在任何事情发生之前消失。它存储为零,因为没有可用于存储它的小数部分。
在使用之前,您需要了解COMPUTE。没有足够的人做到。绝对不需要指定不需要的字段或小数位的过长。这些是“处理”问题的常用方法,但是没有必要,因为实际问题是形成不良的COMPUTE。
如果您的COMPUTE包含乘法,请先执行此操作。如果它包含除法,那么最后做。这可能需要重新安排公式,但这会给您正确的结果。正如布鲁斯·马丁所指出的那样,截断分为两部分。有一个你得到的,十进制截断通过没有指定足够的(任何)小数位,当你期望一个十进制值的中间结果,和高阶截断,如果您的源字段不够大。始终记住结果字段控制中间结果的大小(十进制和整数)。如果你做这些事情,你的COMPUTE将永远有效。
考虑是否要将最终结果舍入。如果是这样,请使用ROUNDED。如果您希望对中间结果进行舍入,则需要使用单独的COMPUTE或DIVIDE或MULTIPLY来自行完成。
如果您不考虑这些因素,您的COMPUTE将会意外,或有时,或根本不工作,或指定过大或小数位。始终记住结果字段控制中间结果的大小(十进制),其中操作数不包含小数位。
如果您在最终结果中不需要任何小数位,请使用Bruce Martin的第一个COMPUTE:
COMPUTE WS-COMPUTE = (((WS-NUM-1 - WS-NUM-2 + WS-NUM-3) * 100) / WS-DENOM
如果确实需要小数位,请使用Bruce Martin的第一个COMPUTE(是的,同一个),并在最终结果(WS-COMPUTE)上定义小数。
如果您需要舍入结果(0-4向下,5-9向上),请使用ROUNDED。如果你需要一些其他的舍入,用额外的小数位数来指定最终结果超出你的需要,并根据你的规范进行自己的舍入。
如果您查看问题右侧的列,请在Related
下找到现有的问题,这些问题将会/应该为您解答。
您不需要在视线中添加虚假数字或虚假小数位。确保你的最终结果足够大,有足够的小数位,并注意事物的顺序。阅读您的手册,该手册应记录中间结果。如果您的手册未涵盖此内容,那么IBM Enterprise COBOL手册是一个很好的一般参考,以及特定的参考。编程指南将整个附录用于中间结果。
答案 2 :(得分:0)
Cobol的默认值通常为 truncate !! 。这包括中间结果。 因此,小数位将在计算中被截断
你可以尝试:
COMPUTE WS-COMPUTE = (((WS-NUM-1 - WS-NUM-2 + WS-NUM-3) * 100) / WS-DENOM
这可能会导致顶级订单数量减少。 或者你也可以
03 WS-Temp Pic 9(11)V9999 comp-3.
Compute WS-Temp = WS-NUM-1 - WS-NUM-2 + WS-NUM-3.
Compute WS-Temp = (WS-Temp / WS-DENOM) * 100.
Compute WS-COMPUTE = WS-Temp.
更改字段定义:
WS-COMPUTE PIC 9(14).
WS-NUM-1 PIC 9(09)V999.
WS-NUM-2 PIC 9(09)V999.
WS-NUM-3 PIC S9(11)V999 COMP-3.
WS-DENOM PIC 9(09).