Chris Murphy
Chris Murphy

Reputation: 6509

unsigned 16 bit integers in Clojure

I would like to use bitwise functions (bit-shift-right, bit-and etc.) in Clojure where the operands are unsigned 16 bit integers.

A 16 bit integer is a decimal number from 0 to 65535, alternatively a binary number from 0000 0000 0000 0000 to 1111 1111 1111 1111.

For example here 123 is a java.lang.Long, so will produce the wrong answer:

(bit-not 123)

How do I make 123 an unsigned 16 bit integer so that the above produces the correct answer, which is 65412 in decimal?

So 0000 0000 0111 1011 (123) should become 1111 1111 1000 0100 (65412).

Upvotes: 1

Views: 1207

Answers (2)

Thumbnail
Thumbnail

Reputation: 13473

This works:

(->> 123
     bit-not
     (bit-and 16rFFFF))
;65412

You can shorten it to:

(->> 123
     (bit-and-not 16rFFFF))
;65412

We're using longs as proxies for unsigned ints. The JVM has no unsigned ints or longs, regardless of which language you use.

Upvotes: 2

Alex Miller
Alex Miller

Reputation: 70201

Java (and Clojure) do not have an unsigned integer type. Clojure mostly provides only 32-bit signed integer bit operations (other than unsigned-bit-shift-right which is equivalent to the >>> in Java).

Java 8 does have limited support for treating a 16-bit integer as an unsigned integer via new methods on the Integer and Long classes that can do a few unsigned operations (compare, multiply, divide, remainder). See: http://docs.oracle.com/javase/8/docs/api/java/lang/Integer.html

There are external libs that provide this functionality in Java as well like https://github.com/jOOQ/jOOU.

Upvotes: 4

Related Questions