Application Development Discussions
Join the discussions or start your own on all things application development, including tools and APIs, programming models, and keeping your skills sharp.
cancel
Showing results for 
Search instead for 
Did you mean: 

Need Help on CEIL command

tom_wan
Contributor
0 Kudos

Hello Everyone

May I get you help on CEIL command?

I wrote the following test program:

---------->

REPORT  ZTEST_TOM_CALCT.

data:
result type I,
p1 type P DECIMALS 2,
p2 type P DECIMALS 2,
p3 type P DECIMALS 4,
p4 type P DECIMALS 4.


p1 = '5349.00'.
p2  = '0.25'.
p3  = '123.0000'.
p4  = '123.0000'.

result = CEIL( P1 * p2 / p3 * p4 * 100 ).
write result.

data: p_temp type string.
p_temp = P1 * p2 / p3 * p4 * 100 .
write:/ p_temp.

data:c_temp type p.
c_temp = ceil( p_temp ).
write:/ c_temp.

<-------------

The result is:

   133,726

133725.00000000000000

        133,725

I can understand ceil ( 133725.00..) = 133725.

But why

result = CEIL( P1 * p2 / p3 * p4 * 100 ) = 133726 ?

Regards

Tom

1 ACCEPTED SOLUTION

kakshat
Advisor
Advisor
0 Kudos

Hi Tom,

I think I've got it. If you see this link (http://help.sap.com/abapdocu_70/en/ABENNUMBER_TYPES.htm), it mentions that if you use packed numbers then decimals up to 31 places are considered during evaluation of arithmetic expressions. Now, what could be happening is that with 31 decimal places, maybe the computed value has a digit towards the end (something like 133725.0000000000000000000000005). Then, CEIL would return the next integer which is 133726.

As to why it does not give 133726 when we use parentheses around p2/p3, probably in that case, the order of evaluation is different (division first and then the multiplication operations as opposed to the other case in which the expression is evaluated from left to right) which leads to a value that does not have any non-zero digits up to 31 places.

Former Member: This sounds believable to me.

17 REPLIES 17

kakshat
Advisor
Advisor
0 Kudos

Hi Tom,

That's interesting and I guess it has to do with the internal conversions that happen during such arithmetic calculations. Although, I haven't been able to pin-point the exact reason, I did notice that that if you place parentheses around p2/p3, you would get the correct value.

Former Member
0 Kudos

Hi Tom,

Check below code you got all are give same out put .

Output :

   133 725

133725.0000000000

        133 725

DATA:

RESULT TYPE I,

P1 TYPE P DECIMALS 2,

P2 TYPE P DECIMALS 2,

P3 TYPE P DECIMALS 4,

P4 TYPE P DECIMALS 4.

P1 = '5349.00'.

P2  = '0.25'.

P3  = '123.0000'.

P4  = '123.0000'.

RESULT =  P1 * P2 / P3 * P4 * 100 .

RESULT = CEIL( RESULT ).

WRITE RESULT.

DATA: P_TEMP TYPE STRING.

P_TEMP =  P1 * P2 / P3 * P4 * 100  .

WRITE:/ P_TEMP.

DATA:C_TEMP TYPE P.

C_TEMP = CEIL( P_TEMP ).

WRITE:/ C_TEMP.

Regard's

Smruti

former_member946717
Contributor
0 Kudos

Hi Tom,

You are getting 133726 because result is of type I and you are using CEIL here. If the result field is an integer then the ceil of a value will be the lowest integer not less than x. Hope this helps! This is a great learning for me too! Thanks

So in this case, Integer = Ceil(133725) = 133726

You can refer link - http://help.sap.com/saphelp_46c/helpdata/en/92/58c505417011d189ec0000e81ddfac/content.htm

0 Kudos

Hello A N,

Yes, CEIL returns the lower integer not less than the argument passed to it. Now, 133725 is passed to CEIL, it should return 133725 since that satisfies the condition lowest integer not less than 133725.

Moreover, if you simply do a CEIL on an integer value, it does not return the next higher integer value.

0 Kudos

Hi Akshat,

Its NOT LESS THAN so the Result should be not less than 133725 Hence it is passing 133726!

You can check this link for more information.

http://help.sap.com/saphelp_46c/helpdata/en/92/58c505417011d189ec0000e81ddfac/content.htm

In this link, X = 3.1 Ceil (3.1) is passed as 4

0 Kudos

133725 is NOT LESS THAN 133725. So, why shouldn't CEIL return 133725 for 133725?

0 Kudos

Hi Akshat,

It would be better if you read the link for more information.

As per me, 133725 is equal to 133725 and is NOT MORE or LESS than 133725 and is definitely not 'the lowest interger less than 133725'.

And as per my understanding the result should be 'lowest integer not less than 133725(in this case)' which means 133726 which is lowest integer and not less than 133725!

Its better if you read the link. I have understood it this way as per the link so I think the result 133726 is correct!

0 Kudos

Hi Akshat

Also in the link they have said CEIL(3.1) into an integer is 4. They could have said '3'. but 4 is the next lowest integer which is greater than 3.1 (lowest integer NOT LESS THAN 3.1).

Hope you understand from the link! Thanks.

Cheers

0 Kudos

I have read the link. You need to understand that, logically speaking, the following IF condition would evaluate to true

IF NOT ( A < B)

if A and B have the same values.

And, they could not have said CEIL(3.1) = 3 because 3 is not less than the argument (3.1). However, CEIL(3) = 3 is correct because 3 (result) is the lowest integer which is NOT LESS THAN 3 (argument).

If you still don't agree, you can simply test for yourself the results of doing a CEIL(3). I would be curious to know if that returns you 4!

0 Kudos

Hi Akshat,

Firstly, it is not about any IF condition here. There are 2 things here:

1. The result should be LOWEST INTEGER

2. It should be NOT LESS than the argument which means it should be GREATER than the argument.

Which means the Result should be 'LOWEST INTEGER and GREATER THAN the Argument'

Definitely CEIL(3) cannot be 4!  I did not even say it should be 4! It considers the decimal portion. In this case it is 133725.00

This works when the argument is a decimal but the result is an integer

Anyway I don't think this is the right forum to try and explain to each other this way! I understood an explanation and gave it here. Its upto us to analyze on it. Cheers

0 Kudos

Hello A N,

I think as long as the discussion is meaningful and done in a respectful manner, this is the right forum. Like you, there could be others who could interpret NOT LESS THAN to be same as GREATER THAN because there is but a small difference between the two.

By the way, I just tried doing a CEIL( 133725.00 ) and even that returned 133725 and not 133726.

My intention is not to prove that you are incorrect but only to try to make you see what you aren't seeing. I rest my case here.

0 Kudos

Hey Akshat,

Definitely even I am not here to prove anyone incorrect. I thought you were misunderstanding me on the explanation front!

Ok lets continue then:)

Yes you may get CEIL(133725.00) as 133725 but what field was inside the bracket? Was it a packed one with decimal 2? and was the result field an Integer? Can you try it with this? Currently I don't have SAP access hence can't try:(

Actually Tom has also got CEIL(133725.00) as 133725 but the field types have differed. This difference happens only when CEIL(Packed decimal) into an Integer

Please don't rest your case, let's solve this! What say?:)

0 Kudos

Nice to see that you are up for it! (I just hope is not cursing us for prolonging this discussion )

Initially, I had tried with a literal - CEIL( '133725.00' ) but after your last reply, just to be absolutely sure, I used a packed variable with 2 decimals. In both cases, I got the same result - 133725.

By the way, I don't know if you read my very first response to Tom but if parentheses are used around p2/p3 without changing anything else, the correct value (133725) is obtained. So, I think this has something to do with how the system evaluates the expression and the internal conversions that go into it.

0 Kudos

Hi Akshat,

Yes I saw about the paranthesis, even I thought about that first. But when I searched online, I got the above link so I am little confused

I already told Tom Wan this is a good post for us to learn something new so I guess he will be happy 

Btw did you paste his code and see how it works!? And what is that link trying to say or do I just forget it? As I have got confused because of that link.:(

kakshat
Advisor
Advisor
0 Kudos

Hi Tom,

I think I've got it. If you see this link (http://help.sap.com/abapdocu_70/en/ABENNUMBER_TYPES.htm), it mentions that if you use packed numbers then decimals up to 31 places are considered during evaluation of arithmetic expressions. Now, what could be happening is that with 31 decimal places, maybe the computed value has a digit towards the end (something like 133725.0000000000000000000000005). Then, CEIL would return the next integer which is 133726.

As to why it does not give 133726 when we use parentheses around p2/p3, probably in that case, the order of evaluation is different (division first and then the multiplication operations as opposed to the other case in which the expression is evaluated from left to right) which leads to a value that does not have any non-zero digits up to 31 places.

Former Member: This sounds believable to me.

0 Kudos

Brilliant Akshat!:)

0 Kudos

Hi everyone

I wrote a program like below:

--->

REPORT  ztest_tom_calct.

DATA:

result_i TYPE i,

p1 TYPE p DECIMALS 2,

p2 TYPE p DECIMALS 2,

p3 TYPE p DECIMALS 4,

p4 TYPE p DECIMALS 4.

p1 = '5349.00'.

p2  = '0.25'.

p3  = '123.0000'.

p4  = '123.0000'.

WRITE:/ 'Case0: Original'.

result_i = CEIL( p1 * p2 / p3  * p4 * 100 ).

WRITE:/ result_i.

*If we split the steps

  1. SKIP.

WRITE:/ 'Case1: If we split the steps like below,we can get 133726'.

DATA result_temp_2 TYPE p DECIMALS 2.

DATA result_temp_4 TYPE p DECIMALS 4.

result_temp_2 = p1 * p2.

WRITE:/ result_temp_2.

result_temp_4 = result_temp_2 / p3.

WRITE:/ result_temp_4.

result_temp_4 = result_temp_4 * p4.

WRITE:/ result_temp_4.

result_temp_4 = result_temp_4 * 100.

WRITE:/ result_temp_4.

result_i = CEIL( result_temp_4 ).

WRITE:/ result_i.

*If 133725.0000000000000000000000005 is the reason

  1. SKIP.

WRITE:/ 'Case2: If 133725.0000000000000000000000005 is the reason'.

DATA: f_temp TYPE f.

f_temp = p1 * p2 / p3 * p4 * 100 .

WRITE:/ f_temp.

result_i = CEIL( f_temp ).

WRITE:/ result_i.

*Why split like this has a different result?

  1. SKIP.

WRITE:/ 'Case3: Why split like this has a different result with Case1?'.

data: p_temp type p DECIMALS 4.

p_temp = p1 * p2 / p3 * p4 * 100.

write:/ p_temp.

<----

The result is

---->

Case0: Original

   133,726

Case1: If we split the steps like below,we can get 133726

        1,337.25

         10.8720

      1,337.2560

    133,725.6000

   133,726

Case2: If 133725.0000000000000000000000005 is the reason

  1.3372500000000000E+05

   133,725

Case3: Why split like this has a different result with Case1?

    133,725.0000

<-----

If we check abaphelp,we can found:

Determination of a calculation type before the calculation is executed,

taking all operands including the result field into account, is a

feature of ABAP that differs considerably from the way in which other

programming languages perform calculations. To avoid unnecessary

conversions, if possible, all operands and the result field should have

the same numeric data type. Another difference is the decimal rounding

of intermediate results in the calculation type i. In other programming

languages, the decimal places are simply cut off.

So my assumption is:

In case 1,it is calculated with higher internal accuracy which leads to 133726.

Regards,

Yong Luo