Stateful
Stateful

Reputation: 737

Objective-C Integer Arithmetic

I'm trying to calculate some numbers in an iPhone application.

int i = 12;
int o = (60 / (i * 50)) * 1000;

I would expect o to be 100 (that's milliseconds) in this example but it equals 0 as displayed by NSLog(@"%d", o).

This also equals 0.

int o = 60 / (i * 50) * 1000;

This equals 250,000, which is straight left-to-right math.

int o = 60 / i * 50 * 1000;

What's flying over my head here?

Thanks,
Nick

Upvotes: 11

Views: 21921

Answers (7)

High Performance Mark
High Performance Mark

Reputation: 78316

In Objective-C / performs integer division on integer arguments, so 4/5 is truncated to 0, 3/2 is truncated to 1, and so on. You probably want to cast some of your numbers to floating-point forms before performing division.

You're also running in to issues with precedence. In the expression

60 / (i * 50) * 1000

the term inside the parentheses is calculated first, so 60 is divided by 600 which produces the result 0. In

60 / i * 50 * 1000

the first operation is to divide 60 by 12 which gives the result 5 and then the multiplications are carried out.

Upvotes: 20

Mosib
Mosib

Reputation: 1

I think you need to use float here instead of int. It will work the way you want! Will give you answer in decimals as well.

Upvotes: 0

Dima
Dima

Reputation: 39389

All the operations in your expression are performed in integer arithmetic, meaning that the fractional part of each intermediate result is truncated. This means that if you divide a smaller integer by a larger integer you will always get 0.

To get the result you want you must either make sure the operations are performed in a particular order, or you must use floats. For example the result of

int o = (60.0 / (i * 50.0)) * 1000.0;

should be o = 100.

Upvotes: 0

R.. GitHub STOP HELPING ICE
R.. GitHub STOP HELPING ICE

Reputation: 215193

Replace:

int o = (60 / (i * 50)) * 1000;

with:

int o = 1200/i;

Upvotes: 1

Alex Reynolds
Alex Reynolds

Reputation: 96937

By order of precedence, the operation:

60 / (12 * 50) 

is performed before multiplying by 1000.

This value is less than 1 and is cast to an int, which truncates it to 0. And 0 times anything is 0.

Use a float or first multiply by 1000 to ensure you're not ending up with propagating a 0 in your calculations.

Upvotes: 0

Neth
Neth

Reputation: 439

It's doing integer math. 60 / (12 * 50) is 0.1, truncates to 0.

Should work if you force floating point and then cast back to an integer.

int o = (int)(60.0 / ((double) i / 50.0) * 1000.0;

Probably not really necessary to make everything a double.

Upvotes: 1

Dave DeLong
Dave DeLong

Reputation: 243146

An integer divided by an integer is an integer.

so 60/600 is not 0.1, it is 0.

Cast (or declare) some stuff as float instead.

Upvotes: 4

Related Questions