Go Down

### Topic: Can someone explain this? [solved] (Read 2070 times)previous topic - next topic

#### dgoldman

##### Oct 14, 2012, 02:50 amLast Edit: Oct 14, 2012, 07:16 am by Nick Gammon Reason: 1
I have, what I thought was a pretty straightforward multiplication operation, but....

Code: [Select]
`uint32_t p =0;void setup(){  Serial.begin(9600);  p = 15*60*1000;  Serial.print("Trial 1: "); Serial.println(p);  p = 15*60;  p = p*1000;  Serial.print("Trial 2: "); Serial.println(p);  p = 15*60;  p *= 1000;  Serial.print("Trial 3: "); Serial.println(p);}void loop(){}`

Yields:
Trial 1: 4294949792
Trial 2: 900000
Trial 3: 900000

What the f@!#^*?

I can't figure out why Trial 1 give such a wacky number. I thought it was wrap around or maybe the way print works, but as you can see the other trials work just fine. So what is going on? And here I thought I understood this stuff...

-- Thanks!

#### PaulS

#1
##### Oct 14, 2012, 03:25 am
Literals, like 15, 60, and 1000, are interpreted as ints, in the absence of any directive to the contrary. Nothing in the first calculation is larger than an int, so ints are used in the calculation. The result overflows an int. That the result is stored in a long is irrelevant.

In the second case, 15 * 60 is an int, stored in a long. Then the long is multiplied by an int, which is promoted to a long. The result is a long, which is stored in a long.

The third case is identical to the second. p = p * 1000 is identical to p *= 1000.

#### el_supremo

#2
##### Oct 14, 2012, 03:28 am
15*60 = 900 which fits into a 16-bit integer.
900*1000 = 900000 which doesn't fit. The result is truncated to 16-bit and sign-extended.
900000 = DBBA0 (hex). Truncate to 16 bits = BBA0. This is negative so sign-extend it to 32 bits FFFFBBA0. This value is then stored in p. Converting this as an unsigned 32-bit integer to decimal gives 4294949792.

Pete
Don't send me technical questions via Private Message.

#### dgoldman

#3
##### Oct 14, 2012, 07:16 am
Ahhh, that makes a lot of sense.  I knew it had to do something with the size of the variable, just couldn't see how.
Thanks a lot for the help!

#### dgoldman

#4
##### Oct 14, 2012, 07:18 am
So could I do something like this:

p = 15L*60L*1000L to force the operation to use longs for the calculation.

#### PaulS

#5
##### Oct 14, 2012, 01:53 pm
Quote
So could I do something like this:

p = 15L*60L*1000L to force the operation to use longs for the calculation.

Yes, you could. And should.

L = long
UL = unsigned long