我正在声明一个带内联声明的变量.问题是输出结果不正确.
DATA(exact_result) = 50 * ( 2 / 5 ) .
cl_demo_output=>display( exact_result ).
Run Code Online (Sandbox Code Playgroud)
任何人都可以建议为什么结果为零,其中50*(2/5)= 20.
问候,
奥马尔阿卜杜拉
内联声明根据右侧(RHS)表达式中的类型分配数据类型.使用算术表达式,编译器根据整体计算类型确定数据类型.
首先,2和5被认为是类型I(4字节整数),因此即使运算符是除法(在该精确情况下为整数除法),结果也是类型I的结果.
然后,50也被认为是类型I,并且因为它与另一个I型数据对象(子表达式2/5的类型I的结果)一起使用,结果也是类型I.
因此,在您的示例中,EXACT_RESULT分配了类型I.
在运行时,由于LHS和RHS数据对象都是I类型,因此计算类型也是I.因此,2/5等于0.4,它被舍入为0,因为它是整数除法,默认的ABAP舍入是"半上升"(0.4的舍入给出0,但0.5得1).
解决方法是明确地定义的数据类型EXACT_RESULT为小数点后具有数字(DECFLOAT16,DECFLOAT34,P型与小数,F和甚至C,因为则计算类型为P!),因为LHS的类型将具有优先级高于RHS(I)的类型,因此计算将从LHS变量的类型推导出来.
DATA(exact_result) = CONV decfloat16( 50 * ( 2 / 5 ) ).
Run Code Online (Sandbox Code Playgroud)
小心这个下一个解决方案:正如我所说,C导致P类型和许多小数的计算,所以我们可以认为这个例子是一个很好的解决方案:
DATA(exact_result) = '50' * ( 2 / 5 ). " equals 20
Run Code Online (Sandbox Code Playgroud)
但是对于内联声明,P计算类型会导致P类型的数据对象,但小数点后面会有0位数,因此结果将被其他数字截断(此处为8而不是50):
DATA(exact_result) = '8' * ( 2 / 5 ). " rounded ! (3 instead of 3.2)
Run Code Online (Sandbox Code Playgroud)