<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />Geschichte, Teil 1
Am frühen Nachmittag spielt die Spätoktobersonne mit dem Jungen und seinen Freunden.Es ist noch nicht beängstigend. Halloween ist Stunden entfernt.
( Eine neu gestaltete JMP User Community kommt!Teil 2 und Teil 3 finden Sie dort! )
Video und Code
Diese Videosequenz zeigt Simulated Annealing zum gleichmäßigen Platzieren von 3200 Punkten um eine Kugel.Zunächst werden die Punkte in einer Doppelspirale vom Nordpol zum Südpol gelegt.Ich habe nicht nach einer Doppelspirale gesucht; Ich hatte auf etwas mehr Anfangsspreizung gehofft, aber es funktioniert trotzdem.Die Farben dienen nur der Visualisierung.Nach den Anfangspunkten beginnt der Glühprozess.https://en.wikipedia.org/wiki/Annealing_(Metallurgie) beschreibt einen physikalischen Glühprozess, bei dem Metall erhitzt wird, um eine kristallisierte Struktur zu entspannen, wodurch sich die Atome in eine andere Beziehung bewegen können.Einige Materialien könnten sogar in der Wärme der Oktobersonne geglüht werden.Die JSL hier ist für das Video optimiert und nicht für irgendetwas anderes optimiert ... aber gut genug.Während der Glühphase steuert ein Heiz- und Kühlplan, wie weit sich die Punkte von ihrem nächsten Nachbarn entfernen dürfen.Da an den Polen viele Punkte zusammengedrängt sind, muss der Zeitplan das System eine Weile heiß halten, damit diese Punkte Zeit haben, sich zu entfernen.Bei dieser „hohen Temperatur“ springen die Punkte weit genug, dass sie oft zu weit in die Nachbarschaft eines anderen Punktes gehen.Die allmähliche Abkühlungsphase des Zeitplans lässt die Punkte sich beruhigen und bewegt sich immer weniger.Das Video endet, bevor sie sich vollständig beruhigt haben.
https://www.youtube.com/watch?v=8-Fjw1wD-Oc

Knoten = 3200;
xx = -nKnoten * 3 / 2;
nodelocs = J( nnodes, 3, 0 ); // x,y,z-Punkt für jeden Knoten
For( i = 1, i <= nnodes, i++,
f = i / nKnoten; // 0..1
z = Cos( f * Pi() ); // oben nach unten
r = Sin( f * Pi() ); // Radius
x = Sin( 10000 * f ) * r; // 10.000 Radianten
y = Cos (10000 * f) * r; // ist viel zu viele.Aber es funktioniert...
nodelocs[i, 1] = x;
nodelocs[i, 2] = y;
nodelocs[i, 3] = z;
);
//nodeobj = Szenenanzeigeliste(); nodeobj<
addnodes = Function( {thisnnodes},
{inode, delta, pos = [0 0 0], result = Scene Display List()},
For( inode = 1, inode <= thisnnodes, inode++,
delta = nodelocs[inode, 0] - pos;
pos = nodelocs[inode, 0];
//zeigen(pos,delta);
result << translate( delta );
rgb = Farbe zu RGB (Wärmefarbe (Inode / nnodes, "spectral")) * 1;
//show(inode/nnodes,rgb);
result << color( rgb[1], rgb[2], rgb[3] );
result << sphere( .005, 3, 3 )//calllist( nodeobj );
;
);
Ergebnis << translate( -pos ); // Ursprünglichen Speicherort wiederherstellen
Ergebnis // gibt die Anzeigeliste zurück
;
);
//a=addnodes();
// Animiere die Knoten zu einer Kugel mit Radius 1 um 0,0,0
anpassen = Funktion( {d},
{inode, radius, next, dist, err, pos, newlocs = J( nnodes, 3, . ), table = KDTable( nodelocs )},
For( inode = 1, inode <= nnodes, inode++,
pos = nodelocs[inode, 0];
// vom nächsten Nachbarn wegschubsen
Tabelle << Zeilen entfernen ( Inode );
{am nächsten, Abstand} = Tabelle << knearestrows( 5, pos );
Tabelle << Zeilen einfügen ( Inode );
For(iclose = 1, iclose <= 5, iclose++,
err = pos - nodelocs[nächste[iclose], 0] + J( 1, 3, Random Normal( 0, .01 ) ); // [dx dy dz]
//Pos = Pos + .00991/ Fehler; // wegziehen
For( idim = 1, idim <= 3, idim++,
Wenn (fehler[idim] < 0,
pos[idim] -= d / iclose,
pos[idim] += d / iclose
)
);
);
// Schubradius in Richtung 1.000
Radius = Sqrt( Summe( pos
pos ) );
// Fehler = 1,0 - Radius; // Fehler ist positiv, wenn Radius zu klein
pos = pos / Radius; // big err bewegt sich schneller
newlocs[inode, 0] = pos; // temporäre Kopie
);
nodelocs = newlocs; // temp nach aktuell kopieren
0 // Dummy-Rückgabewert
;
);
Winkel = 30;
Szene = Szenenkasten ( 1924 / 2, 1084 / 2 );
build = Function( {thisnnodes},
{},
Szene << löschen;
Szene << ShowArcBall(nie/*immer*/ /*Während des Ziehens*/ );
Szene << Hintergrundfarbe (schwarz);
Szene << Perspektive( 65, .1, 5 );
Szene << Translate( 0.0, 0.0, -2.0 );
Winkel += 0,1;
Szene << drehen (Winkel * 0,23, 1, 0, 0);
Szene << drehen (Winkel * 0,11, 0, 1, 0);
Szene << drehen (Winkel * 2, 0, 0, 1);
Objekt = addnodes ( thisnnodes );
Szene << ArcBall( Objekt, 1 );
);
bauen (1);
New Window( "Dot World", Szene );
Für( ich = 1, ich <= 3200, ich += 4,
bauen ( ich );
Szene << aktualisieren;
Warte( 0 );
// scene<
);
For( i = 1, i < 5000, i++, // fast fertig bei 1000
vint = Interpolieren ( i, 1, .00001, 100, .0005, 200, .001, 4000, .0005, 5000, .00001 );
Show( i, vint );
bauen (3200);
Szene << aktualisieren;
Warte( 0 );
anpassen (vint);
//scene<
);
bauen();
Szene << aktualisieren;
Warte( 0 );