Create custom bit length objects
Forgive my English if the title isn't self-explicative.
Here's my problem: I'm writing a program in which I use long variables as containers for two 32-bit integers representing floats with Float.floatToIntBits(). Since a "long" is 64-bit long, it works, two 32-bit variables fit in. The problem is that I've realized that I need to represent 4 floats in a single variable, and I don't think there exist 128-bit objects. Can I create them?
Thanks to anyone
[480 byte] By [
simopal6a] at [2007-11-26 17:48:56]

Hi,Take a look at the BitSet class.Kaj
I'll byte: why do you need to wedge 4 floats into a single variable?
I'm using genetic algorithms to minimize the energy spent by a robot (might seem complicated, but actually isn't). Each individual of the algorithm's popolation is represented as a binary string containing speed and position of each joint; the robot's got two joints, so it's 4 variables.
edit: perhaps there are better ways :-) this is the first way to do this i've thought of.
Message was edited by:
simopal6
Hmmm... If the data really is 4 floats why not define a class or even just a "struct":
public class JointState {
public float x;
public float y;
public float dx;
public float dy;
}
... why did you feel the need to pack two floats into a long?
I've taken a look at BitSet, but I couldn't find a simple way to convert a BitSet to a number. Is this possible?
I don't know if it's possible. I do know that I would not try weird stuff like that before determining that the normal stuff (like a class containing four float values) was unsuitable.
> I've taken a look at BitSet, but I couldn't find a
> simple way to convert a BitSet to a number. Is this
> possible?
Let's step back a little. Is a robot's joint state best descibed by four floating point numbers or by a vector of 128 bits? Or by something else?
> Hmmm... If the data really is 4 floats why not define
> a class or even just a "struct":
> > public class JointState {
>public float x;
> public float y;
>public float dx;
> public float dy;
> }
>
> ... why did you feel the need to pack two floats into
> a long?
Because the algorithm uses an operator (called "crossover", biology term) that takes a binary substring from each of two of those variables, and switches the two sequences (i.e., the first one is put in the second variable, and the second sequence is put in the first variable where there was the first sequence...). I think this is easier to handle if i have a single string rather than 4.
> > I've taken a look at BitSet, but I couldn't find a
> > simple way to convert a BitSet to a number. Is
> this
> > possible?
>
> Let's step back a little. Is a robot's joint state
> best descibed by four floating point numbers or by a
> vector of 128 bits? Or by something else?
Actually, I need each variable represents a robot arm, which has two joints. Each joint has a position and a speed. So to represent one arm a need 4 float (2 for each joint).
edit: sorry, I didn't answer to your question. Four single floats would be better, but are not suitable for the operations used in the algorithm.
Message was edited by:
simopal6
> Because the algorithm uses an operator (called
> "crossover", biology term) that takes a binary
> substring from each of two of those variables, and
> switches the two sequences (i.e., the first one is
> put in the second variable, and the second sequence
> is put in the first variable where there was the
> first sequence...). I think this is easier to handle
> if i have a single string rather than 4.
Well, that certainly doesn't sound like a float operation! Perhaps a structure with 4 ints would work. Are you familiar with bitwise operations:
http://java.sun.com/docs/books/tutorial/java/nutsandbolts/op3.html
> > Because the algorithm uses an operator (called
> > "crossover", biology term) that takes a binary
> > substring from each of two of those variables, and
> > switches the two sequences (i.e., the first one is
> > put in the second variable, and the second
> sequence
> > is put in the first variable where there was the
> > first sequence...). I think this is easier to
> handle
> > if i have a single string rather than 4.
>
> Well, that certainly doesn't sound like a float
> operation! Perhaps a structure with 4 ints would
> work. Are you familiar with bitwise operations:
>
> http://java.sun.com/docs/books/tutorial/java/nutsandbo
> lts/op3.html
I actually use the integer values that i get with Float.floatToIntBits(float).
Here's the code i've used so far for 2 floats:
long value; // the union of the floats
int v1_bits = Float.floatToIntBits(v1); // first float
long v2_bits = Float.floatToIntBits(v2); // second float, need to use long because of later shifting
value &= 0;
value |= v1_bits;
value |= (v2_bits << 32);
Where are the floats coming from in the first place? This is getting more and more curious!
Here's a description of what I have to do.
Suppose I have two possible combinations of speed and position of the joints in a robot arm, represented by 4-bit values:
ARM 1
- JOINT 1
speed: 1000
position: 1011
- JOINT 2:
speed: 0111
position: 1100
ARM1 binary representetion: 1000101101111100
ARM 2
- JOINT 1
speed: 0110
position: 1110
- JOINT 2
speed: 0010
position: 1111
ARM2 binary representetion: 0110111000101111
Crossover works this way:
Random 6-bit sequence from ARM 1: 1000101101111100
Random 6-bit sequence from ARM 2: 0110111000101111
After crossover:
ARM 1: 1000110111111100
ARM 2: 0101101000101111
Thanks for the description. It sounds like an arm consists of 16 bits of data, which can be viewed as the speed and poisiton of two joints, etc...
You can ultimately represent that anyway you like, altough storing it in a float seems curious, to say the least. For the purpose of the crossover operation, having the state of an arm in a BitSet or a short is convenient because then you can do bitwise operations on either data type easily. For example, here is how I would do the crossover in your example:
import java.util.*;
public class Test {
public static final int BIT_LENGTH = 16;
public static void main(String[] args) {
BitSet arm1 = new BitSet(BIT_LENGTH);
BitSet arm2 = new BitSet(BIT_LENGTH);
//initialise -- manually, here. You could do better
//1000101101111100
arm1.set(0);
arm1.set(4);
arm1.set(6);
arm1.set(7);
arm1.set(9);
arm1.set(10);
arm1.set(11);
arm1.set(12);
arm1.set(13);
//0110111000101111
arm2.set(1);
arm2.set(2);
arm2.set(4);
arm2.set(5);
arm2.set(6);
arm2.set(12);
arm2.set(13);
arm2.set(14);
arm2.set(15);
//crossover
int bits = 6;
int start1 = 4;
int start2 = 1;
for(int i=0; i<bits; ++i) {
//classic swap
boolean temp = arm1.get(start1+i);
arm1.set(start1+i, arm2.get(start2+i));
arm2.set(start2+i, temp);
}
}
}
Doing this cross over with 2 16 bit shorts would be an exercise in bitwise operations, and faster of course, because you would be getting and setting the 6 bits in parallel.>
I hadn't seen the second page..!The BitSet would be good, but how can I convert it into a number?Moreover, I need to use floats, because I represent position and speed as numbers. Why do you think they're not suitable?
> The BitSet would be good, but how can I convert it into a number?
With a BitSet of size 16, you could convert it to a short like this:
static short toShort(BitSet arm) {
short value = 0;
for(int i=0; i<15; ++i)
if (arm.get(i))
value |= (1<<i);
return value;
}
That's assuming get(0) is the least significant bit -- I think I got it backwards in my example and made get(0) the high bit -- woops.
> Moreover, I need to use floats, because I represent
> position and speed as numbers? Why do you think
> they're not suitable?
I can't stop you from using floats, but they have values like 3.1415 and 1.08E-13. I thought a position or a speed was repsented by 4 bits of data.
How can I convert a float (or whatever numeric type) to a BitSet?About the use of floats, I know that they're excessively precise, but I need to use floating point numbers, and a float is the littlest one (or isn't it?).
> but I need to use floating point numbersCould you give me an example where you need to use a floating point number? Your description of the problem (4 bits position and 4 bits speed per joint) made no mention of floating point data.
I used 4-bit values to simplify the description of the problem. Actually, position and speed are the arguments needed by a mathematical function which evaluates the fitness of the arm (i.e., how much energy it needs to move at that speed to the specified position), so they have to be precise enough.
In the end, it sounds like sometimes you need to view the state of an arm as a sequence of bits (for that crossover operation) and other times you need to produce floating point values, because they are required by some mathemetical functions.
Perhaps what you need to do is think of the Arm as an abstraction, and write out its specification, then worry about its implementation:
class Arm {
public Joint getJoint1() {...}
public Joint getJoint2() {...}
public void crossOver(Arm otherArm) {...}
public ? fitness() {}
...
}
Well, the only problem is the crossover function...I think I'll try to represent all floats inside a BitSet, do the crossover, and then get back to the binary representation of the number like you did with your example with short numbers...
I guess that ultimately, it doesn't matter how you represent the state -- float(s), int(s), long(s) bitset(s) -- what matters is that you have correct translations between representations. In the end, you can choose the most convenient or most efficient representation.
You're right..!Thanks for you help..!