5

I'm writing a very computationally intense procedure for a mobile device and I'm limited to 32-bit CPUs. In essence, I'm performing dot products of huge sets of data (>12k signed 16-bit integers). Floating point operations are just too slow, so I've been looking for a way to perform the same computation with integer types. I stumbled upon something called Block Floating Point arithmetic (page 17 in the linked paper). It does a pretty good job, but now I'm faced with a problem of 32 bits just not being enough to store the output of my calculation with enough precision.

Just to clarify, the reason it's not enough precision is that I would have to drastically reduce precision of each of my arrays' elements to get a number fitting into a 32-bit integer in the end. It's the summation of ~16000 things that makes my result so huge.

Is there a way (I'd love a reference to an article or a tutorial) to use two 32-bit integers as most significant word and least significant word and define arithmetic on them (+, -, *, /) to process data efficiently? Also, are there perhaps better ways of doing such things? Is there a problem with this approach? I'm fairly flexible on programming language I use. I would prefer C/C++ but java works as well. I'm sure someone has done this before.

Phonon
  • 12,013
  • 12
  • 57
  • 111
  • 8
    I have a stupid question - why can't you use a long, which is 64 bit even on a 32 bit cpu? – MJB Jun 10 '11 at 14:47
  • The stupid answer is yes you can. I was mislead by a piece of documentation. Thanks = ) – Phonon Jun 10 '11 at 14:54
  • Consider switching to native code. – Seva Alekseyev Jun 10 '11 at 14:55
  • @MJB In fact `long` is typically 32 bits on a 32 bit system (although this isn't required) while `long long` if available is the 64 bit integral type. – Mark B Jun 10 '11 at 14:56
  • 2
    Not in java it ain't - on java - short is always 16 bit, integer 32 bit, long 64 bit. No long longs here – MJB Jun 10 '11 at 14:58
  • 1
    C++ interpretation of how many bits assign to data types is compiler dependent. In Java, you always get the same bit representation. – Phonon Jun 10 '11 at 18:28

5 Answers5

7

I'm pretty sure that the JVM must support a 64-bit arithmetic long type, and if the platform doesn't support it, then the VM must emulate it. However, if you can't afford to use float for performance problems, then a JVM will probably destroy you.

Most C and C++ implementations will provide 64-bit arithmetic emulated for 32bit targets- I know that MSVC and GCC do. However, you should be aware that you can be talking about many integer instructions to save a single floating-point instruction. You should consider that the specifications for this program are unreasonable, or perhaps that you could free performance from somewhere else.

Puppy
  • 138,897
  • 33
  • 232
  • 446
  • *"if you can't afford to use float for performance problems, then a JVM will probably destroy you."* - not true. Many phones run JVM just fine, but don't have an FPU, making floating-point operations expensive. Some of them don't even support native apps, because the OS itself is written in Java. – BlueRaja - Danny Pflughoeft Jun 10 '11 at 14:58
  • @BlueRaja: Sure, but the JVM costs an awful lot more to run than having to emulate floating-point. – Puppy Jun 10 '11 at 15:05
  • 2
    Not necessarily. There are some common processors (such as the ARM926) which have no FPU, but which do have hardware acceleration to translate Java bytecode into native instructions on the fly, making Java almost as fast as native code. – Mike Seymour Jun 10 '11 at 16:09
4

Yes, just use 64 bit integers:

long val; // Java

#include <stdint.h>
int64_t val; // C
phihag
  • 245,801
  • 63
  • 407
  • 443
2

There is a list of libraries on the wikipedia page about Arbitrary Precision Arithmetic. Perhaps something on there would work for you?

Chris Shaffer
  • 30,701
  • 4
  • 45
  • 61
2

If you can use Java, the short answer is: Use Java long's. The Java standard defines a long as 64 bits. Any JVM should implement this or it is not compliant with the standard. Nothing requires the CPU to support 64-bit arithmetic. If it's not natively supported, a JVM should implement it with software.

If you really have some crippled Java that does not support long's, use BigInteger. This handles integers of any arbitrarily-large size.

Jay
  • 25,388
  • 9
  • 54
  • 105
2

Talking about C/C++.
Any normal compiler would support "long long" type as 64-bit integrs with all normal arithmetic.
Combined with -O3, it gets very good chances of outputting best possible code for 64-bit arithemtic on your platform.

Andrei
  • 7,898
  • 10
  • 32
  • 41