A&A Title Image Startseite | Programme: Wellenoptik | Algorithmen, Lektionen, Analysen | Unsere Vorläufer | Kontakt, Datenschutz

VdS-Journal 89-91: Einführung in die Wellenoptik

Schnell-Anwahl:
VdS-Journal 89 – Wellenoptik: Licht besteht nicht aus Strahlen
VdS-Journal 90 – Sternabbildung eines Newton-Teleskops
VdS-Journal 91 – Optische Fehler – Die Zernicke-Polynome

VdS-Journal 89: Wellenoptik – Licht besteht nicht aus Strahlen

Das Programm simuliert die Beugung an einem optischen Spalt. Das ist die einfachste Anordnung, and der man Wellenoptik erproben kann.


# Programm Spalt.yp - Beugung am Spalt
from math import *
from turtle import *
from random import *

def Plot(x,y, thickness, col): # einen Punkt setzen
    color(col)
    penup()
    goto(x,y)
    pendown()
    dot(thickness)
    hideturtle()

def plot(x,y):
    Plot(x,y,3, 'black')
    

def Line(x0,y0,x1,y1, thickness, col):
    color(col)
    width(thickness)
    penup(); goto(x0,y0)
    dx=x1-x0; dy=y1-y0
    pendown()
    if (dx<1e-10):
        setheading(90)
        forward(dy)
    else:
        setheading(180*atan(dy/dx)/pi)
        forward(sqrt(dx*dx+dy*dy))
    hideturtle()

def line(x0,y0,x1,y1):
    Line(x0,y0,x1,y1, 1, 'black')

def greenline(x0,y0,x1,y1):
    Line(x0,y0,x1,y1, 1, 'lightgreen')

# Koordinatensystem
def initKoor(x0,x1,stepX, y0,y1,stepY):
    tracer(0,0) 
    setworldcoordinates(x0-0.01*(x1-x0),y0-0.01*(y1-y0),x1+0.01*(x1-x0),y1+0.01*(y1-y0))
    line(x0,y0,x0,y1)
    line(x0,y0,x1,y0)
    x=x0;y=y0
    while (y<=y1):
        line(x,y,x+0.01*(x1-x0),y)
        write(y,font=('Arial',10))
        if y>y0+1e-10:
            greenline(x+0.01*(x1-x0),y,x1,y)
        y=y+stepY
    x=x0;y=y0
    while (x<=x1):
        line(x,y,x,y+0.01*(y1-y0))
        #line(x,y+0.01*(y1-y0),x,y1)
        write(x,font=('Arial',10))
        if x>x0+1e-10:
            greenline(x,y+0.01*(y1-y0),x,y1)
        x=x+stepX
    update()

def sq(x): # Quadratfunktion
    return x*x
 
# Main - Beugung am Spalt
scr=600
I = [0 for i in range(scr)] # Bild
D=0.1    # Abstand zum Schirm
w=0.1    # Breite des Schirms
b=2.5e-6 # Breite des Spaltes
S=1000   # Anzahl Elementarwellen

l=0.555e-6 # lambda 555nm
for i in range (scr):         # jeder Punkt des Schirms...
    X=i*w/2/scr               # X läuft über den halben Schirn
    Q=sqrt(sq(D)+sq(X))       # Länge vom Schlitz-Zentrum
    for j in range (S+1):
        x=-b/2+j/S*b          # x läuft über den ganzen Schlitz
        q=sqrt(sq(D)+sq(X-x)) # Länge des betrachteten Wellenzuges
        s=Q-q
        a=cos(2*pi*s/l)/q
        I[i]=I[i]+a
M=0 # maximale Intensität suchen
for i in range (scr):
    a=sq(I[i])
    if a>M:
        M=a
tracer(0,0)
initKoor(0,1000*w,1000*w/10, 0,1,0.25) # Millimeter in x
for i in range (scr):
    a=sq(I[i])
    x=1000*w*i/scr # in mm
    plot(x,a/M) # aud Maximum skaliert
hideturtle();update();done()

VdS-Journal 90: Sternabbildung eines Newton-Teleskops

  
# Programm Airy1.py
# Stern-Abbildung eines Newton-Teleskops
# Nur Obstruktion, keine Aberrationen eingebaut
from math import *
from turtle import *
from random import *

def Plot(x,y, thickness, col): # einen Punkt setzen
    color((col, col, col))
    penup()
    goto(x,y)
    pendown()
    dot(thickness)
    hideturtle()

def plot(x,y):
    Plot(x,y,3, 'black')
    

def Line(x0,y0,x1,y1, thickness, col):
    color(col)
    width(thickness)
    penup(); goto(x0,y0)
    dx=x1-x0; dy=y1-y0
    pendown()
    if (dx<1e-10):
        setheading(90)
        forward(dy)
    else:
        setheading(180*atan(dy/dx)/pi)
        forward(sqrt(dx*dx+dy*dy))
    hideturtle()

def line(x0,y0,x1,y1):
    Line(x0,y0,x1,y1, 1, 'black')

def greenline(x0,y0,x1,y1):
    Line(x0,y0,x1,y1, 1, 'lightgreen')

# Koordinatensystem
def initKoor(x0,x1,stepX, y0,y1,stepY):
    tracer(0,0) 
    setworldcoordinates(x0-0.01*(x1-x0),y0-0.01*(y1-y0),x1+0.01*(x1-x0),y1+0.01*(y1-y0))
    line(x0,y0,x0,y1)
    line(x0,y0,x1,y0)
    x=x0;y=y0
    while (y<=y1):
        line(x,y,x+0.01*(x1-x0),y)
        write(y,font=('Arial',10))
        if y>y0+1e-10:
            greenline(x+0.01*(x1-x0),y,x1,y)
        y=y+stepY
    x=x0;y=y0
    while (x<=x1):
        line(x,y,x,y+0.01*(y1-y0))
        #line(x,y+0.01*(y1-y0),x,y1)
        write(x,font=('Arial',10))
        if x>x0+1e-10:
            greenline(x,y+0.01*(y1-y0),x,y1)
        x=x+stepX
    update()

def mycircle(r, col):
    color((col, col, col))
    penup()
    goto (0,-r)
    begin_fill()
    circle(r)
    end_fill()
    
def sq(x): # Quadrat
    return x*x

# Vorgabewerte
l=0.55e-6 # lambda 555nm
f=0.650 # Brennweite
A=0.105 # Apertur
O=0.0 # Obstruktion, z.B. 0.2

# Bestimmung der Rahmenbedingungen für die Rechnung - Vorläufig eine reine Festlegung
w = 4.5 * 2.44 * l * f / A; # die erforderliche Bildgröße
S=25 # Anzahl der Quellpunkte in jede Koordinatenrichtung
p=50 # Anzahl der Bildpunkte in jede Koordinatenrichtung

# das Ergebnisfeld für die Punkte: zwei Phasenlagen und das Ergebnis in einem 3D-Feld 
I = [[[0 for i in range(p)] for j in range(p)] for k in range(3)]

G = A * A / 4 / f; # Pfeiltiefe
print(p,":")
for i in range(p): # jeder Bildpunkt X
    print(i, end=" ", flush=True)
    X = -w / 2 + i * w / (p-1)
    for j in range (p): # jeder Bildpunkt Z
        Z = -w / 2 + j * w / (p-1)
        for m in range(S): # Quellkoordinate x
            x = -A / 2.0 + m * A / S
            for n in range(S): # Quellkoordinate z
                z = -A / 2.0 + n * A / S
                r = sqrt(x * x + z * z)
                phi = atan2(z, x)
                if (r <= A / 2):  # nur der Kreis
                    if (r >= O * A / 2): # zentrale Obstruktion berücksichtigen
                        y = sq(r) / 4 / f
                        g = G - y
                        Y = f - y
                        Q = G + sqrt(sq(X) + sq(f) + sq(Z)) # Q ist für einen Quellpunkt unveränderlich 
                        q = g + sqrt(sq(x - X) + sq(Y) + sq(z - Z))
                        s = Q - q
                        for o in range(2): # beide Phasenwinkel
                            phasenwinkel =  o * pi / 2
                            a = cos(2 * pi * s / l  + phasenwinkel) / sq(q)
                            I[o][i][j] = I[o][i][j] + a

# beide Phasen summieren nach I[2]
M = 0 
for i in range(p):
    for j in range(p):
        for o in range(2):
            I[o][i][j] = sq(I[o][i][j])
            a = I[o][i][j]
            I[2][i][j] += a
            if (I[2][i][j] > M):
               M = I[2][i][j]

# Normalisierung und Ausgabe
tracer(0,0)
bgcolor("black")
for i in range(p):
    for j in range(p):
        a = I[2][i][j] / M
        Plot(i-p/2, j-p/2, 2, a**0.7) # die Potenz 0,7 verbessert den Kontrast dunkler Strukturen
        # Plot(i-p/2,j-p/2,2,a)

hideturtle();update();done()

VdS-Journal 91: Optische Fehler – Die Zernicke-Polynome

 
# Programm Zernicke1.py
# Optische Fehler – Die Zernicke-Polynome
# rechnet lange, v.a. bei starkem Defokus
from math import *
from turtle import *
from random import *

def Plot(x,y, thickness, col): # einen Punkt setzen
    color((col, col, col))
    penup()
    goto(x,y)
    pendown()
    dot(thickness)
    hideturtle()

def plot(x,y):
    Plot(x,y,3, 'black')
    

def Line(x0,y0,x1,y1, thickness, col):
    color(col)
    width(thickness)
    penup(); goto(x0,y0)
    dx=x1-x0; dy=y1-y0
    pendown()
    if (dx<1e-10):
        setheading(90)
        forward(dy)
    else:
        setheading(180*atan(dy/dx)/pi)
        forward(sqrt(dx*dx+dy*dy))
    hideturtle()

def line(x0,y0,x1,y1):
    Line(x0,y0,x1,y1, 1, 'black')

def greenline(x0,y0,x1,y1):
    Line(x0,y0,x1,y1, 1, 'lightgreen')

# Koordinatensystem
def initKoor(x0,x1,stepX, y0,y1,stepY):
    tracer(0,0) 
    setworldcoordinates(x0-0.01*(x1-x0),y0-0.01*(y1-y0),x1+0.01*(x1-x0),y1+0.01*(y1-y0))
    line(x0,y0,x0,y1)
    line(x0,y0,x1,y0)
    x=x0;y=y0
    while (y<=y1):
        line(x,y,x+0.01*(x1-x0),y)
        write(y,font=('Arial',10))
        if y>y0+1e-10:
            greenline(x+0.01*(x1-x0),y,x1,y)
        y=y+stepY
    x=x0;y=y0
    while (x<=x1):
        line(x,y,x,y+0.01*(y1-y0))
        #line(x,y+0.01*(y1-y0),x,y1)
        write(x,font=('Arial',10))
        if x>x0+1e-10:
            greenline(x,y+0.01*(y1-y0),x,y1)
        x=x+stepX
    update()

def mycircle(r, col):
    color((col, col, col))
    penup()
    goto (0,-r)
    begin_fill()
    circle(r)
    end_fill()
    
def sq(x): # Quadrat
    return x*x


# Main

# Vorgabewerte
l=0.55e-6 # lambda 555nm
f=650 # Brennweite
A=0.105 # Apertur
O=0.0 # Obstruktion, z.B. 0.2
# die Aberrationen
D=-2 # Defokus
k=1 # Kugelgestaltsfehler
K=0 # Koma
a=0 # Astigmatismus

# Bestimmung der Rahmenbedingungen für die Rechnung - abängig vom Defokus

# die erforderliche Bildgröße
if abs(D)<1:
    w = 4.5 * 2.44 * l * f / A
else:
    w = 4.5 * D * 2.44 * l * f / A
# Anzahl der Quellpunkte
S=25
if (D > 2):
   S = 0.5*S  * D;
# Anzahl der Bildpunkte
p=50
if (D > 4):
   p = p + int((D - 4) * p / 5);

# das Ergebnisfeld für die Punkte: zwei Phasenlagen und das Ergebnis in einem 3D-Feld
I = [[[0 for i in range(p)] for j in range(p)] for n in range(3)]

G = A * A / 4 / f; # Sagitta
print(p,":")
for i in range(p): # jeder Bildpunkt X
    print(i, end=" ", flush=True)
    X = -w / 2 + i * w / (p-1)
    for j in range (p): # jeder Bildpunkt Z
        Z = -w / 2 + j * w / (p-1)
        for m in range(S): # Quellkoordinate x
            x = -A / 2.0 + m * A / S
            for n in range(S): # Quellkoordinate z
                z = -A / 2.0 + n * A / S
                r = sqrt(x * x + z * z)
                phi = atan2(z, x)
                if (r <= A / 2):  # nur der Kreis
                    if (r >= O * A / 2): # zentrale Obstruktion berücksichtigen
                        y = sq(r) / 4 / f
                        g = G - y
                        Y = f - y
                        Q = G + sqrt(sq(X) + sq(f) + sq(Z)) # Q ist für einen Quellpunkt unveränderlich und kann hoch
                        q = g + sqrt(sq(x - X) + sq(Y) + sq(z - Z))
                        R = r / (A / 2); # Zernicke - R
                        # alle Aberration gehen als +- in die Rechnung ein, deshlab müssen
                        # die Abweichungen halbiert werden um ptv zu erhalten
                        # Defokus
                        Q = Q + D * l * (2 * 0 * 0 - 1) / 2; 
                        q = q + D * l * (2 * R * R - 1) / 2;
                        # sph Aberration
                        Q = Q + k * l * (6 * 0 * 0 * 0 * 0 - 6 * 0 * 0 + 1) / 2; 
                        q = q + k * l * (6 * R * R * R * R - 6 * R * R + 1) / 2;
                        # Koma
                        Q = Q + K * l * (3 * 0 * 0 * 0 - 2 * 0) * sin(phi) / 2; 
                        q = q + K * l * (3 * R * R * R - 2 * R) * sin(phi) / 2;
                        # Astigmatismus
                        Q = Q + a * l * 0 * 0 * cos(2 * phi) / 2;
                        q = q + a * l * R * R * cos(2 * phi) / 2;
                        # gesamter Laufzeitunterschied
                        s = Q - q
                        for o in range(2): # beide Phasenwinkel
                            phasenwinkel =  o * pi / 2
                            a = cos(2 * pi * s / l  + phasenwinkel) / sq(q)
                            I[o][i][j] = I[o][i][j] + a

# beide Phasen summieren nach I[2]
M = 0 
for i in range(p):
    for j in range(p):
        for o in range(2):
            I[o][i][j] = sq(I[o][i][j])
            a = I[o][i][j]
            I[2][i][j] += a
            if (I[2][i][j] > M):
               M = I[2][i][j]

# Normalisierung und Ausgabe
tracer(0,0)
bgcolor("black")
for i in range(p):
    for j in range(p):
        a = I[2][i][j] / M
        Plot(i-p/2, j-p/2, 2, a**0.7) # die Potenz 0,7 verbessert den Kontrast dunkler Strukturen
        # Plot(i-p/2,j-p/2,2,a)

hideturtle();update();done()