Maxwell's Demon
Week 1
As an introduction to learning how to model things mathematically, we were
asked to model Maxwell's Demon. I chose to use
Processing for my model because of its ease in graphic interfacing, and I
have recently been learning it for another class, so it helped to give me
some good extra practice with it.
To begin, the canvas size is set up, and the array of particle objects is
instantiated. Then, I draw the bounding box of the model and the gate that is
controlled by the demon. Each particle is then moved based on its speed, and
displayed on the screen. The particle object includes a random color, a random
position and speed (within constraints), a set diameter, and a boolean used
to determine if the particle is passing through the gate. Displaying each
particle is as simple as drawing a circle at the correct position.
I then ensure that the particles are staying within the boundaries of the model
by flipping the sign of its x- and y-velocity when it encounters a wall in
that direction. When the particle approaches the gate in the middle of the
model, it checks to see if the gate is closed or if the particle wasn't already
in the process of passing through, then bounces or lets the particle pass
through accordingly.
To determine if the gate is close or not, the "demon" simply looks at from which
side and how fast the particle is approaching the gate. The total speed is
calculated by taking the square root of the squares of the x- and y-speed.
If that total speed is more than half of the set maximum speed of the particles,
then it is allowed to pass from the left side of the model to the right side,
but will then be stuck on the right side. If the total speed is less than or
equal to half of the max speed, the particle is allowed to pass from the right
side to the left side, and will then be stuck there.
Here is the my simulation as it appears run through Processing:
As can be seen, the faster moving particles can pass from left to right,
but not from right to left, and the slower moving particles can pass from
right to left, but not from left to right. Here is code for my simulation
with the same parameters for reference:
int gate_width = 10; // Width of the gate in the middle of the model
int numParticles = 30; // Number of particles simulated in the model
int fill_white = 255; // Fill canvas with white
int fill_black = 0; // Fill gate with black
int rgb_min = 0; // RGB from 0 to 255
int rgb_max = 255;
int particle_diameter = 30; // Diameter of all particles
int max_speed = 4; // Max speed of all particles
Particle[] particles; // Declare array of particles
void setup() { // Set canvas size, initialize all particles
size(1200,600);
particles = new Particle[numParticles];
for (int i = 0; i < particles.length; i++) {
particles[i] = new Particle();
}
}
void draw() { // Draw white background, draw gate, move and display all particles
noStroke();
fill(fill_white);
rect(0,0,width,height);
fill(fill_black);
rect(((width/2)-(gate_width/2)),0,gate_width,height);
for (int i = 0; i < particles.length; i++) {
particles[i].move();
particles[i].display();
}
}
class Particle { // Particle object contains color, x and y positions, x and y speeds,
color c; // diameter, and passing variable used for passing through the gate.
float xpos;
float ypos;
float xspeed;
float yspeed;
float diameter;
boolean passing;
Particle() { // Give particles random color, set diameter, random
float r = random(rgb_min, rgb_max); // position and speed (within constraints), and
float g = random(rgb_min, rgb_max); // initialize to not passing.
float b = random(rgb_min, rgb_max);
c = color(r,g,b);
diameter = particle_diameter;
xpos = random(diameter, (width-diameter));
ypos = random(diameter, (height-diameter));
xspeed = random(-max_speed, max_speed);
yspeed = random(-max_speed, max_speed);
passing = false;
}
void display() { // Draw the particle at its position
fill(c);
ellipse(xpos,ypos,diameter,diameter);
}
void move() { // If a particle hits edge of canvas, have it bounce;
float radius = diameter/2; // if a particle hits the gate while it's closed, have
float newXpos = xpos + xspeed; // it bounce; if not, let it pass through.
float newYpos = ypos + yspeed;
if (((newXpos + radius) >= width) || ((newXpos - radius) <= 0)) {
xspeed *= -1;
passing = false;
}
if (((newYpos + radius) >= height) || ((newYpos - radius) <= 0)) {
yspeed *= -1;
}
if (((newXpos + radius) >= (width/2 - gate_width/2)) &&
((newXpos - radius) < (width/2 - gate_width/2)) && (xspeed > 0)) {
if (!passing && isGateClosed()) {
xspeed *= -1;
passing = false;
}
}
if (((newXpos - radius) <= (width/2 + gate_width/2)) &&
((newXpos + radius) > (width/2 + gate_width/2)) && (xspeed < 0)) {
if (!passing && isGateClosed()) {
xspeed *= -1;
passing = false;
}
}
xpos = newXpos;
ypos = newYpos;
}
boolean isGateClosed() { // Let fast-moving particles pass from left to right side;
boolean gateClosed = true; // let slow-moving particles pass from right to left side.
float speed = 0.0;
speed = sqrt(sq(xspeed) + sq(yspeed));
if (((speed > max_speed/2) && (xspeed > 0)) ||
((speed > 0) && (speed <= max_speed/2) && (xspeed < 0))) {
gateClosed = false;
passing = true;
}
return gateClosed;
}
}