Wir haben einen hatten Paar von Herausforderungen über die Ulam Spirale. Aber das reicht nicht.
In dieser Herausforderung zeichnen wir eine dreieckige Ulam-Spirale (im Gegensatz zur üblichen quadratischen Ulam-Spirale). Hier ist eine Skizze, wie die Spirale aussieht.
Wie wir wissen, ordnet die Ulam-Spirale alle natürlichen Zahlen in einer äußeren Spirale an und markiert nur diejenigen, die Primzahlen sind. In der obigen Skizze werden also nur die Zahlen angezeigt, die in Schwarz (die Primzahlen) erscheinen.
Die Herausforderung
Akzeptieren Sie eine Zahl N als Eingabe und zeigen Sie die dreieckige Ulam-Spirale bis zu dieser Zahl an.
- Die Eingabe kann stdin oder ein Funktionsargument sein.
- Die Spirale sollte sich in die positive Richtung drehen (dh gegen den Uhrzeigersinn), wie in der obigen Abbildung.
- Jede der 120-Grad-Kurven der obigen Abbildung wäre gültig, und die Kurve kann für verschiedene Eingaben unterschiedlich sein. Die unterste Seite der implizierten Dreiecke sollte jedoch horizontal sein, da die einzigen zulässigen Windungen (Vielfache von) 120 Grad sind.
- Der Code sollte theoretisch (bei genügend Zeit und Speicher) für alle N ausgeführt werden, bis zu dem, was von Zwischenberechnungen, die Sie mit Ihrem Standarddatentyp durchführen, zugelassen wird.
double
ist genug; Keine Notwendigkeit für große Integer-Typen. - Alle eingebauten Funktionen erlaubt.
- Ich werde meine eigene Antwort nicht akzeptieren (nicht, dass ich denke, es wäre sowieso die kürzeste ...).
Ausgabeformate
Wählen Sie eine der folgenden Möglichkeiten.
Zeigen Sie ein Diagramm mit einem Marker (Punkt, Kreis, Kreuz, was auch immer Sie bevorzugen) an Primzahlen und nichts an Nicht-Primzahlen an. Der Maßstab muss für beide Achsen nicht identisch sein. Das heißt, die implizierten Dreiecke müssen nicht gleichseitig sein. Achsen, Gitterlinien und Achsenbeschriftungen sind optional. Es werden nur die Marker bei den Primzahlen benötigt.
Eine Beispielausgabe für N = 12 wäre wie folgt (vergleiche mit der obigen Skizze). Das zweite Diagramm ist ein interessanteres Beispiel, das N = 10000 entspricht.
- Erstellen Sie eine Bilddatei mit dem oben genannten Format in einem bekannten Bildformat (z. B. png, tiff, bmp).
Zeigen Sie die Spirale als ASCII-Grafik an , wobei Sie ein einzelnes Zeichen Ihrer Wahl für Primzahlen und ein Leerzeichen für Nicht-Primzahlen verwenden und ein Leerzeichen, um die Nummernpositionen in derselben Zeile zu trennen. Führende oder nachfolgende Leerzeichen oder Zeilenumbrüche sind zulässig. Zum Beispiel wäre der Fall N = 12 mit
o
als Zeicheno · · · o · o · · · o · o
Wobei natürlich nur die
o
Markierung bei Primzahlen tatsächlich angezeigt würde. Die·
bei Nicht-Primzahlen ist hier nur als Referenz gezeigt.
Gewinnkriterium
Die eigentliche Belohnung ist es, sich selbst von diesen erstaunlichen Mustern zu überzeugen.
quelle
Antworten:
CJam,
4942 BytesEingabe als einzelne Ganzzahl in STDIN. Ausgabe als ASCII-Gitter mit
0
für Primzahlen. Die Drehung der Spirale ist nicht konsistent: Die größte Anzahl der Spiralen befindet sich immer in der unteren Reihe.Teste es hier.
Erläuterung
Die Grundidee ist, das Dreieck während der Berechnung als unregelmäßiges 2D-Array darzustellen. Sie erhalten dieses Array, indem Sie die Zeilen umkehren und alle Zeilen nach links ausrichten:
Wäre dargestellt als
Da wir die Linie gespiegelt haben, möchten wir die Spirale im Uhrzeigersinn aufrollen . Das ist praktisch, denn wir müssen das Dreieck nur gegen den Uhrzeigersinn drehen und der nächsten Unterliste der Reihe nach voranstellen. Wir können das zerlumpte Array drehen, indem wir alle Zeilen umkehren und transponieren:
Also hier ist der Code. Ein Detail, auf das ich aufmerksam machen möchte, ist das letzte Bit, das das dreieckige Layout erstellt. Ich denke das ist ziemlich geschickt. :)
quelle
MATL ,
4836 BytesVerwendet die aktuelle Version (9.3.0) .
Probieren Sie es online!
Keine Ahnung, wie der Online-Compiler es schafft, Grafikausgaben in ASCII zu übersetzen, aber es tutDas erzeugt eine ungefähre ASCII-Darstellung dank einer Octave-Funktion , die vom Online-Compiler unterstützt wird!Bearbeiten (4. April 2016): Die Funktion
Y[
wurdek
seit Release 13.0.0 in umbenannt. Der Link zum Online-Compiler übernimmt diese Änderung, damit der Code getestet werden kann.Beispiel
erzeugt die grafische Ausgabe (gezeigte MATLAB-Version):
Erläuterung
Der Code verwendet komplexe Zahlen, um den Pfad zu verfolgen, dem die Spirale folgt. Wie aus der ersten Figur in der Herausforderung ersichtlich ist, ist jedes gerade Bein der Spirale ein Segment mit zunehmender Länge 1, 2, 3, 4 ... und zyklisch zunehmender Ausrichtung von 120 Grad, 240 Grad, 0 Grad, 120 Grad. ..
Der Code generiert zunächst die einzelnen komplexen Verschiebungen von jeder Ganzzahl zur nächsten. Diese komplexen Verschiebungen haben Größenordnung 1 und Winkel
2*pi/3
,4*pi/3
oder0
(in Radiant). Somit können sie leicht als imaginäre Exponentiale erzeugt werden. Dazu wird zuerst die Ganzzahlfolge 0,1,2,2,3,3,3,4,4,4 ... verwendet.Diese Ganzzahl - Sequenz ist fast wie die „n erscheint n - mal“ -Sequenz ( OEIS A002024 ) und kann , wie sie erhalten werden , in
floor(sqrt(2*n)+.5)
denenn
ist 0,1,2,3, .... Multipliziert man durch2j*pi/3
, woj
die imaginäre Einheit ist , erzeugt die gewünschten komplexen Verschiebungen.Die Verschiebungen werden akkumuliert, um die Positionen zu berechnen, die den ganzzahligen Zahlen in der Spirale entsprechen. Die erste ganze Zahl in der Spirale, die ist
1
, befindet sich willkürlich an der Position1
in der komplexen Ebene.Schließlich werden die Positionen verworfen, die Nicht-Primzahlen entsprechen, und der Rest wird in der komplexen Ebene aufgetragen.
quelle
.png
Datei kopieren, die von der Webseite @AlexAplot(1:5)
) gemacht und es wird eine Textgrafik ausgegeben !! matl.tryitonline.net/#code=NTpYRw&input= @AlexA. Wie ist das??Zeichnen sollte mit erfolgen
LaTeX / PGF, 527
594Bytes527 Bytes ist das vollständige Dokument wie oben, dh einschließlich Präambel und Parameter (hier 4000, also ~ 523 ohne Parameter). Erzeugt eine PDF-Datei.
Grundidee: Nun, zeichne einfach. Verwendet eine Matrixtransformation für ein Dreiecksgitter. Das einzige Problem ist, dass auch die Punkte von der Transformation betroffen (und gestreckt) sind. Also wähle ich für Ellipsen-Marker :) was ich damit meine, wird im zweiten Bild deutlich (n = 250, 5pt).
Eine weitere Einschränkung: Kann aufgrund der maximalen Stapelgröße von TeX nur bis zu etwas weniger als 5000 verarbeiten. Das erste Bild ist für n = 4000. Anscheinend ist es möglich, den Stapel zu vergrößern , ich habe es nicht ausprobiert.
Verwendet PGFs
isprime()
.Ungolfed:
quelle
lualatex
oder eines anderen dynamisch zuweisenden Compilers sollte es Ihnen ermöglichen, die Stapelgröße zu umgehen, wenn ich Ihren entsprechenden Kommentar richtig verstehe. Es ist also keine Einschränkung Ihrer Antwort, nur der meisten Implementierungen, bei denen Sie sie ausführen würden.Mathematica, 94 Bytes
Ergebnis
quelle
Python, 263 Bytes
Als Python-Neuling gibt es sicherlich Verbesserungspotential :)
Beispiel:
quelle
s=[];X=[];Y=[];i=1;x=0;y=0
biss=X=Y=[];i=1;x=y=0;
x=y=0
.R 137 Bytes
Verwendet nur integrierte Funktionen, auch für Primzahlen. Aufgrund seines vektorisierten Ansatzes anstelle eines iterativen Ansatzes ist es schnell, kann jedoch keine großen Zahlen verarbeiten.
Golf gespielt:
Ungolfed:
Beispiel:
quelle