How to get the string as binary IEEE 754 representation of a 32 bit float?
Example
1.00 -> '00111111100000000000000000000000'
Approach : To convert a floating point decimal number into binary, first convert the integer part into binary form and then fractional part into binary form and finally combine both results to get the final answer.
Python float values are represented as 64-bit double-precision values. The maximum value any floating-point number can be is approx 1.8 x 10308. Any number greater than this will be indicated by the string inf in Python.
float() in Python Python float() function is used to return a floating-point number from a number or a string representation of a numeric value.
You can do that with the struct
package:
import struct def binary(num): return ''.join('{:0>8b}'.format(c) for c in struct.pack('!f', num))
That packs it as a network byte-ordered float, and then converts each of the resulting bytes into an 8-bit binary representation and concatenates them out:
>>> binary(1) '00111111100000000000000000000000'
Edit: There was a request to expand the explanation. I'll expand this using intermediate variables to comment each step.
def binary(num): # Struct can provide us with the float packed into bytes. The '!' ensures that # it's in network byte order (big-endian) and the 'f' says that it should be # packed as a float. Alternatively, for double-precision, you could use 'd'. packed = struct.pack('!f', num) print 'Packed: %s' % repr(packed) # For each character in the returned string, we'll turn it into its corresponding # integer code point # # [62, 163, 215, 10] = [ord(c) for c in '>\xa3\xd7\n'] integers = [ord(c) for c in packed] print 'Integers: %s' % integers # For each integer, we'll convert it to its binary representation. binaries = [bin(i) for i in integers] print 'Binaries: %s' % binaries # Now strip off the '0b' from each of these stripped_binaries = [s.replace('0b', '') for s in binaries] print 'Stripped: %s' % stripped_binaries # Pad each byte's binary representation's with 0's to make sure it has all 8 bits: # # ['00111110', '10100011', '11010111', '00001010'] padded = [s.rjust(8, '0') for s in stripped_binaries] print 'Padded: %s' % padded # At this point, we have each of the bytes for the network byte ordered float # in an array as binary strings. Now we just concatenate them to get the total # representation of the float: return ''.join(padded)
And the result for a few examples:
>>> binary(1) Packed: '?\x80\x00\x00' Integers: [63, 128, 0, 0] Binaries: ['0b111111', '0b10000000', '0b0', '0b0'] Stripped: ['111111', '10000000', '0', '0'] Padded: ['00111111', '10000000', '00000000', '00000000'] '00111111100000000000000000000000' >>> binary(0.32) Packed: '>\xa3\xd7\n' Integers: [62, 163, 215, 10] Binaries: ['0b111110', '0b10100011', '0b11010111', '0b1010'] Stripped: ['111110', '10100011', '11010111', '1010'] Padded: ['00111110', '10100011', '11010111', '00001010'] '00111110101000111101011100001010'
Here's an ugly one ...
>>> import struct >>> bin(struct.unpack('!i',struct.pack('!f',1.0))[0]) '0b111111100000000000000000000000'
Basically, I just used the struct module to convert the float to an int ...
Here's a slightly better one using ctypes
:
>>> import ctypes >>> bin(ctypes.c_uint.from_buffer(ctypes.c_float(1.0)).value) '0b111111100000000000000000000000'
Basically, I construct a float
and use the same memory location, but I tag it as a c_uint
. The c_uint
's value is a python integer which you can use the builtin bin
function on.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With