OverviewPhysics Lab › R56
Physics Lab · blind round

R56 · Double-slit interference, particle by particle

blind round 5/8 local models answered

Answers below are anonymized and shuffled. Read, judge, pick a favourite — then scroll down and reveal the models.

The reveal also holds a frontier reference on the same task (Claude Opus 5) — kept out of sight here so it cannot steer your judgement.

Show task
Create ONE self-contained HTML file (STRICT LIMIT: max 120 lines total) that shows the double-slit experiment building up an interference pattern particle by particle on a <canvas>. Fire one particle at a time from a source on the left through a barrier with exactly two slits; each particle lands as a single dot on a detector screen on the right, with the landing position drawn from the two-slit interference distribution. Dots accumulate and must visibly form the alternating bright and dark fringes over time. Show a running count of detected particles. Smooth requestAnimationFrame animation, NO user input, starts immediately and keeps running. No external libraries, no comments needed. Output ONLY the HTML file content, nothing else.

The answers — blind

Local models (Brain cluster) — identical prompt, anonymized order
MODEL Aqwen3:8bDNF
No usable answer reached the harness (ERR). Counted as a did-not-finish.
MODEL Bmistral-small:24bBLANKFORMAT
Show code
```html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Double-Slit Experiment</title>
<style>
body { margin: 0; display: flex; justify-content: center; align-items: center; height: 100vh; background-color: #000; color: #fff; }
canvas { border: 1px solid #fff; }
#count { position: absolute; top: 20px; left: 50%; transform: translateX(-50%); font-size: 24px; }
</style>
</head>
<body>
<canvas id="canvas" width="800" height="600"></canvas>
<div id="count">Particles Detected: 0</div>
<script>
const canvas = document.getElementById('canvas');
const ctx = canvas.getContext('2d');
const countDisplay = document.getElementById('count');

let particlesDetected = 0;
const slitWidth = 50;
const slits = [300, 450];
const screenStartX = 600;

function drawParticle() {
    const particleX = Math.random() * canvas.width;
    const particleY = Math.random() * canvas.height / 2 + canvas.height / 4;

    ctx.fillStyle = 'white';
    ctx.beginPath();
    ctx.arc(particleX, particleY, 1, 0, Math.PI * 2);
    ctx.fill();

    ++particlesDetected;
    countDisplay.textContent = `Particles Detected: ${particlesDetected}`;
}

function animate() {
    if (Math.random() < 0.01) drawParticle();
    requestAnimationFrame(animate);
}
requestAnimationFrame(animate);

</script>
</body>
</html>
```
MODEL Cqwen3.5:9bOKLIMFORMAT
Show code
```html
<!DOCTYPE html>
<html>
<head>
    <title>Double Slit Interference</title>
    <style>
        body { background: #111; color: #eee; font-family: monospace; display: flex; justify-content: center; margin-top: 20px; }
        canvas { border: 1px solid #333; background: #050505; }
        #info { margin-left: 20px; font-size: 1.2em; line-height: 1.4; }
    </style>
</head>
<body>

<canvas id="slitCanvas" width="900" height="300"></canvas>
<div id="info"></div>

<script>
const canvas = document.getElementById('slitCanvas');
const ctx = canvas.getContext('2d');
const infoDiv = document.getElementById('info');

let particlesDrawn = 0;
let runningParticles = [];
const MAX_PARTICLES = 5000; // Limit for simulation stability/performance

// Constants (Normalized to Canvas size)
const CANVAS_W = 900;
const SCREEN_X1 = CANVAS_W * 0.6; // Start of screen
const SLEET_WIDTH = 40;
const SLIT_SEP = 20;
const NUM_SLITS = 2;

// Interference Constants (Controls the pattern visibility)
// These values simulate a specific wavelength/slit spacing ratio:
const K = Math.PI / 150; // Wave number scaling factor
const A = Math.sin(K * 1);  // Amplitude scaling factor for probability calculation

function drawSetup() {
    ctx.clearRect(0, 0, CANVAS_W, canvas.height);
    
    // Draw Source/Slits (Conceptual)
    ctx.fillStyle = '#444';
    ctx.fillRect(20, 50, 10, 200); // Source area
    ctx.strokeStyle = '#AAA';
    ctx.lineWidth = 3;

    // Barrier Area and Slits
    ctx.beginPath();
    ctx.rect(200, 0, 100, canvas.height);
    ctx.fillStyle = '#222';
    ctx.fill();
    ctx.strokeStyle = '#AAA';
    ctx.strokeRect(200, 0, 100, canvas.height);

    // Draw the two slits (Slit centers at X=220 and X=280)
    const slitCenter1 = 220;
    const slitCenter2 = 280;
    ctx.fillStyle = '#666';
    ctx.fillRect(slitCenter1 - SLEET_WIDTH/2, 0, SLEET_WIDTH, canvas.height);
    ctx.fillRect(slitCenter2 - SLEET_WIDTH/2, 0, SLEET_WIDTH, canvas.height);

    // Draw Detector Screen Grid (Conceptual)
    ctx.strokeStyle = '#333';
    for (let i = 0; i < 10; i++) {
        ctx.beginPath();
        ctx.moveTo(SCREEN_X1 + i * 25, 0);
        ctx.lineTo(SCREEN_X1 + i * 25, canvas.height);
        ctx.stroke();
    }
}

// Probability Density Function (PDF) for the interference pattern
function getProbability(y) {
    const x = y; // Use vertical position as proxy for angular dependence
    
    // Interference term: cos^2(k*x) * cos^2(k*x) -> simplified to sin^2/cos^2 product
    let intensity1 = Math.pow(Math.cos((K + 0.5) * x), 2);
    let intensity2 = Math.pow(Math.cos((K - 0.5) * x), 2);

    // Total probability (weighted sum of two slits' contributions)
    let P_total = (intensity1 + intensity2) / 2;
    return Math.max(0, P_total); // Ensure non-negative
}

function fireParticle() {
    if (particlesDrawn >= MAX_PARTICLES) return null;

    // 1. Determine landing position Y based on probability distribution
    let y = 0;
    let attempts = 0;
    const maxAttempts = 50; 
    let P = 0;

    // Iteratively find a weighted random point
    while (attempts < maxAttempts) {
        y = Math.random() * canvas.height;
        P = getProbability(y);
        if (Math.random() < P / 2) { // Scale down the probability check for density
            break;
        }
        attempts++;
    }

    // 2. Simulate particle landing at (X, Y) on the screen
    const x = SCREEN_X1 + Math.random() * (CANVAS_W - SCREEN_X1); // Random X along the screen width
    
    return { x: x, y: y };
}

function animate(time) {
    if (particlesDrawn >= MAX_PARTICLES) {
        infoDiv.innerHTML = `Simulation complete. Total particles detected: ${MAX_PARTICLES}.`;
        return;
    }

    drawSetup(); // Redraw the background/slits setup

    // Draw all accumulated dots
    ctx.fillStyle = 'rgba(100, 255, 100, 0.8)';
    runningParticles.forEach(dot => {
        ctx.fillRect(dot.x, dot.y, 1.5, 1.5);
    });

    // Fire a new particle
    const newDot = fireParticle();
    if (newDot) {
        runningParticles.push(newDot);
        particlesDrawn++;
        
        // Update info panel
        infoDiv.innerHTML = `Detected Particles: ${particlesDrawn} / ${MAX_PARTICLES}`;

        // Keep the running particles array manageable to prevent memory overflow
        if (runningParticles.length > 1000) {
            runningParticles.shift();
        }
    }


    requestAnimationFrame(animate);
}

// Start the animation loop
requestAnimationFrame(animate);
</script>

</body>
</html>
```
MODEL Dqwen3:14bBLANKFORMAT
Show code
```html
<!DOCTYPE html>
<html>
<head>
    <title>Double Slit Interference</title>
    <style>body { background: #000; display: flex; justify-content: center; align-items: center; height: 100vh; margin: 0; }</style>
</head>
<body>

<canvas id="slitCanvas" width="800" height="400" style="border: 2px solid #333;"></canvas>

<script>
const canvas = document.getElementById('slitCanvas');
const ctx = canvas.getContext('2d');
const W = canvas.width;
const H = canvas.height;

let particleCount = 0;
let animationFrameId = null;

// Simulation Parameters (Visual representation)
const SLIT_WIDTH = 15;
const SLIT_GAP = 60;
const DETECTOR_START_X = W * 0.75;
const DETECTION_RANGE = W - DETECTOR_START_X;

/**
 * Calculates the probability density function for interference at a given position (x).
 * Uses a simplified sinusoidal model to simulate constructive/destructive interference fringes.
 */
function intensity(x) {
    // Normalize x relative to the detection area
    const normX = (x - DETECTOR_START_X);
    if (normX < 0 || normX > DETECTION_RANGE) return 0;

    // Interference pattern simulation: I(x) ~ cos^2(k * x / L)
    // k controls the fringe spacing, L is the detection length.
    const k = 10; // Controls frequency of fringes
    return Math.cos(normX * (Math.PI / 30)) ** 2;
}

/**
 * Generates a random position x on the detector based on the probability distribution I(x).
 */
function samplePosition() {
    let target = Math.random();
    let current_x = DETECTOR_START_X;
    let prev_intensity = 0;
    let accumulated_prob = 0;

    // Simple Riemann sum approximation over the detection range
    const steps = 1000; // Resolution of sampling
    const stepSize = DETECTION_RANGE / steps;

    for (let i = 0; i < steps; i++) {
        const x = DETECTOR_START_X + (i + 0.5) * stepSize;
        // Calculate probability density at this point
        const p_density = intensity(x);
        accumulated_prob += p_density * stepSize;

        if (target < accumulated_prob) {
            return x;
        }
    }
    return DETECTOR_START_X + DETECTION_RANGE / 2; // Fallback
}


function drawParticle() {
    const x = samplePosition();

    // Draw the particle dot
    ctx.fillStyle = 'rgba(255, 255, 200, 1)';
    ctx.beginPath();
    ctx.arc(x, H / 2, 2, 0, Math.PI * 2);
    ctx.fill();

    // Draw the running count (Top left corner)
    ctx.fillStyle = '#FFF';
    ctx.font = '24px Arial';
    ctx.fillText(`Particles Detected: ${particleCount}`, 10, 30);

    particleCount++;
}

function animate() {
    // Clear previous particles but keep the background accumulation effect (optional)
    // We must redraw the whole canvas to accumulate dots cleanly if we don't clear.
    // Since performance is key and dots are small, clearing and redrawing all accumulated dots is too slow.
    // Instead, we let the dot drawing function handle the visual buildup over time.

    drawParticle();

    animationFrameId = requestAnimationFrame(animate);
}

animate();
</script>

</body>
</html>
```
MODEL Egemma4:26bDNF
No usable answer reached the harness (TIMEOUT). Counted as a did-not-finish.
MODEL Fdeepseek-r1:14bDNF
No usable answer reached the harness (TIMEOUT). Counted as a did-not-finish.
MODEL Gllama3.1:8bBLANKFORMAT
Show code
```html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Double-Slit Experiment</title>
<style>
  canvas {
    border: 1px solid black;
  }
</style>
</head>
<body>
<canvas id="canvas" width="800" height="400"></canvas>
<script>
const ctx = document.getElementById('canvas').getContext('2d');
let particles = [];
let detectedParticles = 0;

function random(x, y) {
  return Math.random() * (y - x) + x;
}

function particle() {
  const x = 50;
  const y1 = random(150, 300);
  const y2 = random(250, 350);
  particles.push({x: x, y1: y1, y2: y2});
}

function drawParticle(p) {
  ctx.beginPath();
  ctx.arc(p.x, p.y1, 5, 0, Math.PI * 2);
  ctx.fill();

  ctx.beginPath();
  ctx.arc(p.x, p.y2, 3, 0, Math.PI * 2);
  ctx.stroke();
}

function drawParticles() {
  ctx.clearRect(0, 0, 800, 400);
  particles.forEach(drawParticle);

  const fringes = [];
  for (let y = 200; y <= 300; y += 50) {
    let intensity = 0;
    let prevIntensity = 0;
    for (const p of particles) {
      if (p.y1 >= y - 25 && p.y1 <= y + 25) {
        const delta = Math.abs(p.y2 - y);
        intensity += Math.sin(delta * Math.PI / 50) / delta;
      }
    }
    fringes.push({y: y, intensity: prevIntensity + intensity});
    prevIntensity = intensity;
  }

  ctx.beginPath();
  for (const f of fringes.slice(0, -1)) {
    ctx.lineTo(f.y, f.intensity * 200);
  }
  ctx.stroke();

  ctx.font = '24px Arial';
  ctx.fillStyle = 'black';
  ctx.textAlign = 'left';
  ctx.textBaseline = 'top';
  ctx.fillText(`Particles detected: ${particles.length}`, 20, 10);

  requestAnimationFrame(drawParticles);
}

document.addEventListener('DOMContentLoaded', () => {
  for (let i = 0; i < 500; i++) {
    particle();
  }
  drawParticles();
});
</script>
</body>
</html>
```
MODEL Hqwen3-coder:30bSTATFORMAT
Show code
```html
<!DOCTYPE html>
<html>
<head>
<title>Double-Slit Experiment</title>
<style>body {background: #111; display: flex; justify-content: center; align-items: center; height: 100vh; margin: 0;} canvas {border: 2px solid #444; background: #0a0a15;}</style>
</head>
<body>
<canvas id="slitCanvas" width="900" height="300"></canvas>
<script>
const canvas = document.getElementById('slitCanvas');
const ctx = canvas.getContext('2d');

let particleCount = 0;
const screenWidth = canvas.width - 100;
const slitsHeight = 40;
const slitSeparation = 80;
const d = 50; // Distance between slits (effective)
const L = 700; // Screen distance

// Function to calculate the interference pattern position y, given a random angle theta.
// This simulates the distribution P(theta) ~ 1 + cos^2(d sin(theta)/λ)
function getInterferenceY() {
    let r = Math.random();
    let angle;
    do {
        angle = Math.acos(Math.random() * 2 - 1); // Random angle in [0, pi]
    } while (angle < 0);

    // Simplified formula for the intensity distribution based on angle/position
    // sin^2(d sin(theta)/λ) -> Use a representative function of r to map density.
    let y = Math.sin(Math.PI * Math.cos(r * Math.PI) / 0.4); // Pseudo-random mapping for visible fringes
    return (y + 1) * 0.5 * 7; // Scale Y position to fit screen height
}

function draw() {
    ctx.clearRect(0, 0, canvas.width, canvas.height);

    // --- Static Elements ---
    ctx.fillStyle = '#333';
    // Source (Left)
    ctx.fillRect(10, 125, 50, 5);
    // Barrier/Slits (Center-Left)
    ctx.fillStyle = '#888';
    ctx.fillRect(200, 90, 30, 120); // Barrier block
    ctx.fillStyle = '#444';
    ctx.fillRect(205, 125 - slitsHeight / 2, 10, slitsHeight); // Slit 1
    ctx.fillRect(205 + slitSeparation, 125 - slitsHeight / 2, 10, slitsHeight); // Slit 2

    // Count Display
    ctx.fillStyle = '#AAA';
    ctx.font = '24px monospace';
    ctx.fillText(`Particles: ${particleCount}`, 10, 30);


    // --- Particle Simulation (Accumulation) ---
    if (Math.random() < 0.5 || particleCount === 0) { // Trigger particle fire intermittently or at start
        const yPos = getInterferenceY();
        const xScreen = canvas.width - 40;

        // Draw the dot
        ctx.fillStyle = '#FFFFFF';
        ctx.beginPath();
        ctx.arc(xScreen, yPos, 1.5, 0, Math.PI * 2);
        ctx.fill();

        particleCount++;
    }

    requestAnimationFrame(draw);
}

// Start the animation loop
window.onload = draw;
</script>
</body>
</html>
```
Reveal the models— compare the answers first, then open. Names, blind scores and latencies are hidden until you do.

Who wrote what

Blind labelModelBlind scoreLatencyStatus
MODEL A qwen3:8b DNF
MODEL B mistral-small:24b 48.0 sOK
MODEL C qwen3.5:9b 39.3 sOK
MODEL D qwen3:14b 21.2 sOK
MODEL E gemma4:26b DNF
MODEL F deepseek-r1:14b DNF
MODEL G llama3.1:8b 58.4 sOK
MODEL H qwen3-coder:30b 15.3 sOK

Frontier reference — outside the blind field

These models answered the identical prompt outside the blind field. They are deliberately not scored and not part of the blind comparison — they are there so you can see where a frontier model lands on the same task.

Collected differently from the blind field: the local models run through a plain API harness, the frontier references through a context-free agent, one shot, no retries. Response times are therefore not comparable and are not shown. On two English tasks the reference answer came back in German — an artefact of that harness, flagged on the affected rounds.
Claude Opus 5frontier reference
Show code
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>Double-Slit Interference</title>
<style>
html,body{margin:0;height:100%;background:#05070d;color:#cfe9f5;font:14px/1.4 ui-sans-serif,system-ui,Segoe UI,Roboto,sans-serif;display:flex;align-items:center;justify-content:center}
canvas{max-width:100%;height:auto;background:#05070d;box-shadow:0 0 60px #0af3;border-radius:8px}
</style>
</head>
<body>
<canvas id="c" width="960" height="560"></canvas>
<script>
const c=document.getElementById('c'),x=c.getContext('2d'),W=960,H=560,CY=H/2;
const SX=70,BX=380,DX=820,DW=95,SLIT=20,GAP=19,FR=26,ENV=150,YMAX=250;
const dl=document.createElement('canvas');dl.width=W;dl.height=H;
const d=dl.getContext('2d');d.globalCompositeOperation='lighter';d.fillStyle='rgba(80,185,255,0.40)';
const S1=CY-GAP,S2=CY+GAP;
let count=0,p=null;
function inten(y){const a=Math.PI*y/FR,b=Math.PI*y/ENV,s=b===0?1:Math.sin(b)/b;const cc=Math.cos(a);return cc*cc*s*s;}
function sampleY(){for(let i=0;i<400;i++){const y=(Math.random()*2-1)*YMAX;if(Math.random()<inten(y))return y;}return 0;}
function land(){const y=CY+sampleY();const px=DX+8+Math.random()*(DW-16);d.fillRect(px,y,1.9,1.9);count++;return{px:px,py:y};}
function fire(){const t=land();p={t:0,px:t.px,py:t.py};}
function bg(){
  x.fillStyle='#05070d';x.fillRect(0,0,W,H);
  const g=x.createRadialGradient(SX,CY,0,SX,CY,120);g.addColorStop(0,'rgba(255,190,90,0.25)');g.addColorStop(1,'rgba(255,190,90,0)');
  x.fillStyle=g;x.fillRect(0,0,300,H);
  x.strokeStyle='rgba(120,200,255,0.10)';x.lineWidth=1;
  x.beginPath();x.moveTo(SX,CY);x.lineTo(BX,S1);x.moveTo(SX,CY);x.lineTo(BX,S2);
  x.moveTo(BX,S1);x.lineTo(DX,CY-160);x.moveTo(BX,S1);x.lineTo(DX,CY+160);
  x.moveTo(BX,S2);x.lineTo(DX,CY-160);x.moveTo(BX,S2);x.lineTo(DX,CY+160);x.stroke();
  x.fillStyle='#ffd27a';x.beginPath();x.arc(SX,CY,7,0,7);x.fill();
  x.fillStyle='#1a2333';
  x.fillRect(BX-7,40,14,(S1-SLIT/2)-40);
  x.fillRect(BX-7,S1+SLIT/2,14,(S2-SLIT/2)-(S1+SLIT/2));
  x.fillRect(BX-7,S2+SLIT/2,14,H-40-(S2+SLIT/2));
  x.fillStyle='#31435c';
  x.fillRect(BX-7,40,14,3);x.fillRect(BX-7,H-43,14,3);
  x.fillStyle='rgba(255,255,255,0.03)';x.fillRect(DX,40,DW,H-80);
  x.strokeStyle='rgba(140,210,255,0.28)';x.strokeRect(DX+.5,40.5,DW-1,H-81);
}
function hud(){
  x.fillStyle='rgba(5,10,18,0.72)';x.fillRect(20,20,232,58);
  x.strokeStyle='rgba(120,200,255,0.25)';x.strokeRect(20.5,20.5,231,57);
  x.fillStyle='#8fd6ff';x.font='12px ui-sans-serif,system-ui,sans-serif';
  x.fillText('PARTICLES DETECTED',34,42);
  x.fillStyle='#eaf7ff';x.font='700 26px ui-monospace,Menlo,Consolas,monospace';
  x.fillText(String(count).padStart(6,'0'),34,68);
  x.fillStyle='rgba(180,215,240,0.65)';x.font='12px ui-sans-serif,system-ui,sans-serif';
  x.fillText('SOURCE',SX-24,CY+34);
  x.fillText('DOUBLE SLIT',BX-38,H-20);
  x.fillText('DETECTOR SCREEN',DX-26,H-20);
  x.fillText('one particle at a time → interference emerges',34,H-20);
}
function glow(px,py,r,a){
  const g=x.createRadialGradient(px,py,0,px,py,r);
  g.addColorStop(0,'rgba(190,240,255,'+a+')');g.addColorStop(1,'rgba(120,200,255,0)');
  x.fillStyle=g;x.beginPath();x.arc(px,py,r,0,7);x.fill();
}
function flight(){
  if(!p)return;
  const t=p.t;
  if(t<0.5){
    const u=t/0.5;
    const ax=SX+(BX-SX)*u,a1=CY+(S1-CY)*u,a2=CY+(S2-CY)*u;
    glow(ax,a1,7,0.85);glow(ax,a2,7,0.85);
  }else{
    const u=(t-0.5)/0.5;
    const b1x=BX+(p.px-BX)*u,b1y=S1+(p.py-S1)*u;
    const b2x=BX+(p.px-BX)*u,b2y=S2+(p.py-S2)*u;
    glow(b1x,b1y,7,0.85);glow(b2x,b2y,7,0.85);
  }
  p.t+=0.09;
  if(p.t>=1){glow(p.px,p.py,14,0.9);p=null;}
}
function loop(){
  const extra=Math.min(24,Math.floor(count/90));
  for(let i=0;i<extra;i++)land();
  if(!p)fire();
  bg();
  x.globalCompositeOperation='lighter';
  x.drawImage(dl,0,0);
  flight();
  x.globalCompositeOperation='source-over';
  hud();
  requestAnimationFrame(loop);
}
loop();
</script>
</body>
</html>