Why does INT8, INT16, INT32 casting in MATLAB round the values to a different integer from that of Simulink when both are configured to round to the nearest integer?

24 views (last 30 days)
I am using INT8, INT16, INT32 functions in MATLAB to cast tie numbers, for example, -0.5, -1.5, 0.5, 1.5 etc. The documentation of these functions mention that double and single values are rounded to the nearest integer value on conversion. So, when I cast -0.5 to INT8, INT16 or INT32, I receive -1. However, when I use the Data Type Conversion block in Simulink to cast -0.5 to INT8, INT16 or INT32, I receive 0. I have configured the Data Type Conversion block to round the values to the nearest integer value as well. I expect the behavior of MATLAB and Simulink to be identical when performing the same task.

Accepted Answer

MathWorks Support Team
MathWorks Support Team on 27 Jun 2009
The difference in results obtained when casting to INT8, INT16 or INT32 in MATLAB and Simulink is an expected behavior. Rounding is very interesting when it comes to tie values such as -0.5, 0.5, 1.5 etc.
There are three common choices for what happens when rounding a tie:
1. Nearest rounding with ties rounded away from zero
2. Nearest rounding with ties rounded towards +infinity
3. Convergent rounding
MATLAB's ROUND, INT8, INT16, INT32 functions implement (1) rounding as nearest rounding with ties rounded away from zero.
Simulink's blocks provide a choice of 4 - 5 rounding modes one of which is "Nearest". This choice implements rounding option (2) nearest rounding with ties rounded towards +infinity. This is causing the difference in their behavior.
Simulink's behavior of rounding ties towards +infinity is motivated by the efficiency of generated code during the code generation process. Breaking the tie away from zero would require more primative operations (assuming two's complement integers) than breaking the tie towards +infinity.
Fixed-point toolbox, however, straddles between MATLAB and Simulink via the Embedded MATLAB block. Fixed-point toolbox provides several rounding choices including (a) Nearest (b) Convergent. The option (a) Nearest behaves like Simulink where it rounds the tie towards +infinity. Convergent rounding is another type of Nearest rounding with a distinct tie breaker rule. Convergent rounding always breaks ties by rounding to the nearest even value. The purpose for Convergent rounding is to reduce buildup of numerical due to always breaking ties in one direction.
MATLAB round does break ties in two directions, but all positive ties go up and all negative ties go down, so it does have potential for "drift" if the calculation is centered around zero.
Many DSP chips have convergent rounding supported in hardware so this nice rounding behaviour does not have a code size or code speed penalty on those chips. If the target hardware does not provide convergent rounding, then there is a code speed/size penalty.
  1 Comment
Patrik Ek
Patrik Ek on 14 Apr 2014
So extremely annoying. The ceil and floor functions exist for a reason. A proper behaviour of cast would be to truncate the answer...

Sign in to comment.

More Answers (0)

Products

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!