So I have a separate class and function that take a float and convert it to a string of 1’s and 0’s. That then gets passed to another object where I would like to convert the string of 1’s and 0’s to back to the original float. Here is the code I been playing with, let me know if you have any suggestions.
void TestFunc(string s, int startpos, int stoppos)
{
byte[] b = new byte[4];
int bytepos = 0;
for (int i = 0; i < 32; i += 8)
{
print(i);
string a = "";
for (int j = 0; j < 8; j++)
{
a += s[i + startpos];
}
print(a);
b[bytepos] = Convert.ToByte(a);
bytepos += 1;
}
}
Uhm first of all your code doesn’t look like it’s using a “float” anywhere. You pass in a string and only work on single characters. Your “j” loop does simply add the same character 8 times. It also assumes the incoming string has at least 32 characters. Your “a” string would always contain 8 characters. Convert.ToByte expects a string that contains a decimal representation of a byte, i.e. 0 up to 255. You might wanted to use [Convert.ToByte][1] ovreload that takes an additional base where you would pass 2 for binary. However which order your “bits” are in depends on how you actually converted your value to a binary string. Your method just has way too many issues and mistakes.
Why do you actually want to convert it to a string containing binary digits? it’s an incredible waste of space ^^.
Anyways I would recommend to first get the actual binary representation of the float value. You can use a helper struct like this one:
[System.Runtime.InteropServices.StructLayout(System.Runtime.InteropServices.LayoutKind.Explicit)]
public struct FloatHelper
{
[System.Runtime.InteropServices.FieldOffset(0)]
public float floatVal;
[System.Runtime.InteropServices.FieldOffset(0)]
public int intVal;
}
This struct uses a trick to “overlap” the “floatVal” and the “intVal” field in memory so they both occupy the same memory location. That way we can write a float value to floatVal and simply read out the binary representation using the intVal or vice versa. You can simply create two methods like this:
public static string FloatToBinary(float aValue)
{
FloatHelper h = new FloatHelper();
h.floatVal = aValue;
var v = h.intVal;
var sb = new System.Text.StringBuilder(32);
for (int i = 0; i < 32; i++)
sb.Append(((v&(1<<(31-i)))!=0)?'1':'0');
return sb.ToString();
}
public static float BinaryToFloat(string aBinaryStr)
{
if (string.IsNullOrEmpty(aBinaryStr) || aBinaryStr.Length < 32)
throw new System.FormatException("BinaryToFloat expects a binary string of 32 characters");
int v = 0;
for (int i = 0; i < 32; i++)
v |= ((aBinaryStr *== '1') ? 1 : 0) << (31-i);*
FloatHelper h = new FloatHelper();
h.intVal = v;
return h.floatVal;
}
This is untested but BinaryToFloat should recreate the exact same float value from the binary string that is produced by FloatToBinary.
I actually used a similar struct in my [floating point number format editor window][2] which might help to understand how floating point numbers work behind the scenes. There’s also [this online tool][3] which allows you to convert 32bit floats to binary and inspect / manipulate the individual bits.
[1]: Convert.ToByte Method (System) | Microsoft Learn
[2]: GitHub - Bunny83/Floating-Point-Format: Utility EditorWindow for the UnityEditor to view the binary representation of single and double precision floating point format
[3]: IEEE-754 Floating Point Converter