Einführung und Kredit
Heute ohne ausgefallenen Auftakt: Bitte umsetzen takewhile
.
Eine Variation davon (über eine nicht-triviale Datenstruktur) war eine Aufgabe in meinem Kurs für funktionale Programmierung an der Universität. Diese Aufgabe ist jetzt abgeschlossen und wurde im Unterricht besprochen. Ich habe die Erlaubnis meines Professors, sie hier zu posten (ich habe ausdrücklich darum gebeten).
Spezifikation
Eingang
Die Eingabe ist eine Liste (oder das entsprechende Konzept Ihrer Sprache) positiver Ganzzahlen.
Ausgabe
Die Ausgabe sollte eine Liste (oder das entsprechende Konzept Ihrer Sprache) positiver Ganzzahlen sein.
Was ist zu tun?
Ihre Aufgabe ist es, takewhile
(Spracheinbauten sind erlaubt) mit dem Prädikat zu implementieren, dass die betrachtete Zahl gerade ist (sich auf takewhile zu konzentrieren).
Sie durchlaufen die Liste also von Anfang bis Ende und während die Bedingung (gerade) ist, kopieren Sie sie in die Ausgabeliste. Sobald Sie ein Element treffen, das die Bedingung nicht erfüllt, brechen Sie die Operation und die Ausgabe ab (Ein schrittweises Beispiel finden Sie weiter unten). Diese Funktionalität höherer Ordnung wird auch als takeWhile ( takewhile
) bezeichnet.
Mögliche Eckfälle
Die Reihenfolge der Ausgabeliste gegenüber der Eingabeliste darf nicht verändert werden, zB [14,42,2]
darf nicht geändert werden [42,14]
.
Die leere Liste ist eine gültige Ein- und Ausgabe.
Wer gewinnt?
Das ist Code-Golf, also gewinnt die kürzeste Antwort in Bytes!
Es gelten selbstverständlich Standardregeln.
Vektoren testen
[14, 42, 2324, 97090, 4080622, 171480372] -> [14, 42, 2324, 97090, 4080622, 171480372]
[42, 14, 42, 2324] -> [42, 14, 42, 2324]
[7,14,42] -> []
[] -> []
[171480372, 13, 14, 42] -> [171480372]
[42, 14, 42, 43, 41, 4080622, 171480372] -> [42, 14, 42]
Schritt-für-Schritt-Beispiel
Example Input: [42, 14, 42, 43, 41, 4080622, 171480372]
Consider first element: 42
42 is even (21*2)
Put 42 into output list, output list is now [42]
Consider second element: 14
14 is even (7*2)
Put 14 into output list, output list is now [42,14]
Consider third element: 42
42 is even (21*2)
Put 42 into output list, output list is now [42,14,42]
Consider fourth element: 43
43 is not even (2*21+1)
Drop 43 and return the current output list
return [42,14,42]
Antworten:
Mathematica, 18 Bytes
Ein weiterer glorreicher Einbau, der durch Golfsprachen um den Faktor 3 übertroffen wird, ohne den eingebauten ...
quelle
Haskell, 13 Bytes
span
Teilt die Eingabeliste in ein Listenpaar kurz vor dem ersten Element auf, in dem das Prädikat (->even
) falsch ist.fst
Nimmt das erste Element des Paares.Alternative Version, 13 Bytes:
break
ist das Gegenteil vonspan
, dh es teilt die Liste am ersten Element, an dem das Prädikat wahr ist.Natürlich gibt es auch
aber das sind 14 bytes.
quelle
MATL , 6 Bytes
Probieren Sie es online!
Erläuterung
quelle
to~Y<)
funktioniert auch, aber ich mag dieses besser :-)Hexagony , 19
Lesbar:
Probieren Sie es online!
Dies kann wahrscheinlich durch ein oder zwei Bytes golfen werden, aber das erfordert möglicherweise ein wirklich ausgeklügeltes Layout, das mit brachialer Gewalt leichter gefunden werden kann (selbst wenn es ziemlich lange dauert, es zu finden).
Erklärung auf hohem Niveau
Das Programm folgt meistens diesem Pseudocode:
Was missbraucht, wie Hexagony versucht, eine Zahl zu lesen, wenn STDIN leer ist (es gibt eine Null zurück). Vielen Dank an Martin für die Hilfe bei der Entwicklung dieses Ansatzes.
Vollständige Erklärung
Ich habe immer noch nicht mit Mono rumgespielt, um Timwis fantastische esoterische IDE zum Laufen zu bringen, also habe ich mich darauf verlassen, dass Martin mir einige hilfreiche, hübsche Bilder liefert!
Zunächst eine kleine Einführung in den grundlegenden Kontrollfluss in Hexagony. Der erste Befehlszeiger (IP), der als einziger in diesem Programm verwendet wird, beginnt oben links im hexagonalen Quellcode und bewegt sich nach rechts. Wenn die IP die Kante des Sechsecks verlässt, werden die
side_length - 1
Reihen in Richtung der Mitte des Sechsecks verschoben. Da dieses Programm ein Sechseck mit einer Seitenlänge von drei verwendet, verschiebt sich die IP in diesem Fall immer um zwei Zeilen. Die einzige Ausnahme ist, wenn es sich von der mittleren Reihe wegbewegt, wo es sich abhängig vom Wert der aktuellen Speicherkante bedingt nach oben oder unten im Sechseck bewegt.Nun ein bisschen zu den Bedingungen. Das einzige in conditionals Hexagony für Steuerfluß ist
>
,<
und die mittlere Kante des Sechsecks. Diese folgen alle einer konstanten Regel: Wenn der Wert an der aktuellen Speicherflanke Null ist oder der negative Kontrollfluss sich nach links bewegt und wenn er positiv ist, fließt der Kontrollfluss nach rechts. Die Klammern größer als und kleiner als lenken die IP in Winkeln von 60 Grad um, während die Kante des Sechsecks steuert, zu welcher Zeile die IP springt.Hexagony hat auch ein spezielles Speichermodell, bei dem alle Daten an den Rändern eines unendlichen hexagonalen Gitters gespeichert werden. Dieses Programm verwendet nur drei Kanten: eine zum Speichern von zwei, eine für die aktuell gelesene Nummer und eine für die Nummer modulo zwei. Es sieht ungefähr so aus:
Ich werde nicht zu jedem Zeitpunkt während der Erläuterung des Programms sorgfältig erklären, wo wir uns im Speicher befinden. Kommen Sie also hierher zurück, wenn Sie verwirrt sind, wo wir uns im Speicher befinden.
Mit all dem kann die eigentliche Erklärung beginnen. Zuerst füllen wir die "2" -Kante im Speicher mit einer 2, führen dann ein No-Op aus und bewegen den Speicherzeiger nach rechts (
2.}
).Als nächstes beginnen wir die Hauptprogrammschleife. Wir lesen die erste Zahl von STDIN und treffen dann eine Bedingung (
?<
). Wenn in STDIN keine Zahlen mehr vorhanden sind, liest dies eine Null in die aktuelle Speicherflanke, sodass wir nach links auf die abbiegen@
, die das Programm beendet. Andernfalls hüpfen wir von einem Spiegel, bewegen den Speicherzeiger nach hinten und nach links, wickeln uns um das Sechseck, um den Rest der Division der Eingabe durch 2 zu berechnen, und drücken dann eine andere Bedingung (/"%>
).Wenn der Rest eins war (dh die Zahl war ungerade), biegen wir nach rechts ab und folgen dem blauen Pfad oben, indem wir das No-Op erneut ausführen. Dann wickeln wir uns bis zum Ende des Sechsecks um, multiplizieren die aktuelle Kante mit 10 und addieren dann Acht, hüpfen Sie von ein paar Spiegeln, multiplizieren und addieren Sie erneut, setzen Sie 188 auf die aktuelle Kante, führen Sie den No-Op erneut aus und beenden Sie schließlich das Programm (
.8/\8.@
). Dieses verworrene Ergebnis war ein glücklicher Zufall, ich hatte ursprünglich ein viel einfacheres Stück Logik geschrieben, aber festgestellt, dass ich es zugunsten des No-Ops entfernen konnte, von dem ich dachte, dass es eher im Sinne von Hexagony war.Wenn der Rest Null war, biegen wir stattdessen links ab und folgen dem roten Pfad oben. Dies bewirkt, dass wir den Speicherzeiger nach links bewegen und dann den Wert (den Eingabewert) als Zahl ausgeben. Der Spiegel, dem wir begegnen, wirkt aufgrund der Richtung, in die wir uns bewegen, wie ein No-Op (
{/!
). Dann treffen wir die Kante des Sechsecks, die eine Bedingung mit nur einem Ergebnis darstellt, da der Eingabewert von zuvor bereits als positiv getestet wurde, sodass wir uns immer nach rechts bewegen (wenn Sie sich vorstellen, in Richtung der IP zu blicken). . Wir multiplizieren dann die Eingabe mit 10 und addieren zwei, nur um die Richtung zu ändern, wickeln den neuen Wert um und überschreiben ihn mit dem ASCII-Wert des Großbuchstabens M, 77. Dann schlagen wir einige Spiegel und verlassen ihn über den Rand der Mitte von das Sechseck mit einem Trampolin (2<M\>$
). Da 77 positiv ist, bewegen wir uns ganz nach unten und überspringen wegen des Trampolins die erste Anweisung (!
). Wir multiplizieren dann die aktuelle Speicherflanke mit 10 und addieren 8, um 778 zu erhalten. Wir geben dann diesen Wert mod 256 (10) als ASCII-Zeichen aus, was zufällig Newline ist. Schließlich verlassen wir das Sechseck und kehren zum ersten zurück,?
der den 778 mit dem nächsten Eingabewert überschreibt.quelle
Pyth,
1397 BytesDank an @FryAmTheEggman für 2 (ziemlich knifflige) Bytes!
Erläuterung:
Teste es hier .
quelle
G
s eingeführt werden, eine für die Bedingungs%R2G
und eine als Argument für die FunktionP
.Gelee , 5 Bytes
Probieren Sie es online! oder überprüfen Sie alle Testfälle .
Wie es funktioniert
quelle
Python 2,
4342 BytesDie Funktion ändert ihr Argument an Ort und Stelle .
Vielen Dank an @xnor für das clevere Golfen!
Teste es auf Ideone .
quelle
"1'"in`map(bin,x)`
ed, 13
Da echte Programmierer verwenden den Standard - Texteditor .
Übernimmt die Eingabe als eine Ganzzahl in jeder Zeile. Ausgänge im gleichen Format.
Dies findet einfach die erste ungerade Zahl (die mit einer ungeraden Ziffer endet) und löscht von dieser Zeile bis zum Ende der Datei.
quelle
Clojure, 21 Bytes
Endlich ist Clojure fast konkurrierend! (Dank der eingebauten Aufgabe) Sehen Sie es online https://ideone.com/BEKmez
quelle
Python,
4544 BytesTeste es auf Ideone .
quelle
R, 25 Bytes
Oder äquivalent
quelle
05AB1E,
87 BytesErläuterung
Probieren Sie es online aus
Vorherige 8-Byte-Lösung
Erläuterung
Probieren Sie es online aus
quelle
Brainf ***, 263 Bytes
Ich habe ein kleines Stück von hier genommen
Ich würde eine Erklärung geben, aber selbst ich habe keine Ahnung mehr, wie das funktioniert.
Erwartet Eingaben als durch Leerzeichen getrennte Zahlen (zB
2 432 1
)quelle
+
und>
eine Logik verwenden?>
s effizienter machen, aber ich verstehe sie jetzt nicht genugPyth, 7 Bytes
Probieren Sie es hier aus!
Was ich in Pyke versucht habe, aber der Index ist in dieser Atmosphäre kaputt
quelle
Schläger, 22 Bytes
Das
λ
Zeichen wird mit 2 Bytes gezählt.Ich habe noch nie einen Schläger gesehen, der in einer der Code-Golf-Antworten verwendet wurde, die ich gesehen habe, also musste ich es mindestens einmal tun!
quelle
Labyrinth , 14 Bytes
Eingabe und Ausgabe sind durch Zeilenvorschub getrennte Listen (obwohl die Eingabe grundsätzlich ein beliebiges nicht-stelliges Trennzeichen verwenden könnte).
Probieren Sie es online!
Dies ist wahrscheinlich das kompakteste Labyrinth-Programm, das ich je geschrieben habe.
Interessanterweise
takewhile(odd)
ist viel einfacher:Erläuterung
Der übliche Labyrinth-Primer:
?
in diesem Fall) und bewegt sich nach Osten.Der Hauptfluss durch das Programm ist eine einzelne Schleife um den Umfang:
Zufällig wissen wir, dass die Oberseite des Stapels danach Null ist
!
und"
sich die IP garantiert nicht zur Mitte hin dreht.`
und%
andererseits werden sie als Bedingungen verwendet, bei denen sich die IP in Richtung der Mitte bewegen kann, so dass@
das Programm beendet wird, oder sie kann sich weiterhin um den Umfang bewegen.Schauen wir uns den Code in der Schleife an:
Und dann beginnt die Schleife von vorne.
Das wirft die Frage auf, warum dies
takewhile(odd)
so viel einfacher ist. Es gibt zwei Gründe:0
(was gerade ist) zurückgegeben wird, benötigen wir keine separate EOF-Prüfung. Die Liste würde an dieser Stelle sowieso abgeschnitten.N % 2
ist0
(im Gegensatz zu1
), die Mittel statt bedingter Steuer fließen können wir einfach die andere Kopie dividierenN
durchN % 2
: wenn der Eingang ungerade ist, dass nur BlätterN
und wir sogar losgeworden von derN % 2
(so dass wir don‘ t need;
), aber wenn die Eingabe gerade ist, wird das Programm einfach mit einem (stillen) Division-durch-Null-Fehler beendet.Daher ist der andere Code eine einfache Schleife, die überhaupt keine Verzweigung zulässt.
quelle
Brachylog ,
1916 BytesErläuterung
Heute habe ich einen netten Trick gelernt (der in der 19-Byte-Antwort verwendet wurde): Ist
~b.hH
kürzer als:[H]rc.
das Anhängen eines Elements am Anfang einer Liste. Das erste bedeutet "Ausgabe ist das Ergebnis mit einem zusätzlichen Element am Anfang, und das erste Element der Ausgabe istH
" , während das andere direkt "Ausgabe ist die Verkettung von[[H], Result]
" ist.quelle
J 10 Bytes
Erläuterung
quelle
1{.2&|<;._2]
ist interessant (obwohl länger)$
statt{.
Python, 41 Bytes
Kürzt
l
bis zum Index des ersten Auftretens einer ungeraden Zahl. Der Index wird gefunden, indem1
in den Werten modulo nach a gesucht wird2
. Um zu verhindern, dass eine ungerade Zahl gefunden wird,1
wird a am Ende gesetzt.quelle
C #, 50 Bytes
quelle
a=>a.TakeWhile(x=>x%2<1);
CJam , 11 Bytes
Vielen Dank an @Dennis für zwei Korrekturen und ein Byte!
Dies ist ein Codeblock (äquivalent zu einer Funktion; standardmäßig zulässig), der das Eingabearray auf dem Stapel erwartet und das Ausgabearray auf dem Stapel belässt.
Probieren Sie es online!
Erläuterung
quelle
Retina , 17 Bytes
Der Zeilenvorschub am Ende ist signifikant. Eingabe und Ausgabe sind durch Leerzeichen getrennte Listen.
Probieren Sie es online!
Dies ist eine einfache Regex-Ersetzung, sie entspricht der ersten ungeraden Zahl (dh einer Zahl, die mit einer ungeraden Ziffer endet) und, wenn möglich, dem Leerzeichen davor sowie allem, was danach steht, und ersetzt sie durch eine leere Zeichenfolge, dh alle Elemente von dort ab werden aus der Eingabe entfernt.
Wie Leaky Nun hervorhebt, können wir 6 Bytes einsparen, wenn wir die Liste in Binärform nehmen, aber es scheint ein bisschen betrügerisch zu sein, also werde ich wahrscheinlich die Dezimalversion weiter zählen:
quelle
JavaScript (Firefox 30-57), 30 Byte
quelle
V , 13 Bytes
Probieren Sie es online!
Erläuterung:
Praktischerweise überprüft derselbe Code alle Testfälle gleichzeitig.
quelle
Dyalog APL , 11 Bytes
2|
Division Rest von der Teilung mit 2~
negieren∧\
AND-Scan (schaltet ab der ersten 0 aus)/⍨
wähle woquelle
Ruby, 25 Bytes
Ich glaube ich verliere ...
quelle
->a{a.take_while &:even?}
oder zumindest->a{a.take_while(&:even?)}
?Pyke, 8 Bytes
Dolmetscher behoben, andere Links verwenden
Verwendet Dennis 'Methode, außer dass meine split_at-Funktion die Änderung enthält - wahrscheinlich ein Fehler
Oder mit Bugfix, 7 Bytes
Probieren Sie es hier aus!
Oder nach dem 2. Bugfix 6 Bytes
Probieren Sie es hier aus!
Erläuterung:
quelle
GolfScript, 11 Bytes
Dies ist ein vollständiges GolfScript-Programm, das ein stringifiziertes GolfScript-Array-Literal (z. B.
[28 14 7 0]
) liest und dasselbe Array mit dem ersten ungeraden Element und allem, was danach entfernt wurde, ausgibt :Probieren Sie es online aus. (Auch: Erweiterte Version mit Testgeschirr. )
De-Golf-Version mit Kommentaren:
Diese Lösung basiert auf dem GolfScript-Filteroperator
{ },
, der den Inhalt des Codeblocks für jedes Element eines Arrays ausführt und die Elemente des Arrays auswählt, für die der Code im Block einen wahren Wert (dh einen Wert ungleich Null) zurückgibt oben auf dem Stapel.So
{1&},
würden beispielsweise alle ungeraden Zahlen in einem Array und{~1&},
alle geraden Zahlen ausgewählt. Die Herausforderung besteht also darin, einen Filter zu erstellen, der gerade Zahlen auswählt, bis er die erste ungerade Zahl findet , und danach überhaupt keine Zahlen mehr auswählt.Die Lösung, die ich verwendet habe, besteht darin, die konstante Bitmaske
1
(die zum Extrahieren des niedrigsten Bits jeder Eingabenummer verwendet wird) durch eine Variable im Stapel zu ersetzen, die das Ergebnis (0 oder 1) der vorherigen Filterschleifeniteration speichert (und auf initialisiert wird) 1 vor der Schleife). Sobald der Filter also einmal 0 zurückgibt, wird auch die Bitmaske auf 0 gesetzt, so dass der Filter nie wieder 1 zurückgibt.quelle
Viertens 114 Bytes
Forth hat eigentlich keine Listen. Die Parameter müssen in umgekehrter Reihenfolge auf den Stack geschoben werden, wie es für Forth typisch ist. Das Ergebnis bleibt in der gleichen Reihenfolge auf dem Stapel. Dies funktioniert auf Ideone aus irgendeinem Grund nicht, aber auf repl. Die neue Zeile wird benötigt, um Mehrdeutigkeiten zu beseitigen.
Probieren Sie es online aus
Ungolfed, mit Kommentaren:
Dieses Programm (mein vorheriger Versuch) druckt die Ergebnisse, bis es eine ungerade Zahl erreicht. Alles, was übrig bleibt (nicht genommen), bleibt auf dem Stapel.
Schlägt fehl, wenn nur ganze Zahlen
quelle
Befunge, 35 Bytes
Dieser Code verarbeitet Zahlen zwischen 0 und 65535
Eingabeformat :
Hier ist eine Version, die die Werte am Ende des Prozesses anzeigt:
Sie können den Code hier testen , müssen jedoch eine nachgestellte Zeile mit nachgestellten Leerzeichen hinzufügen, wie in dieser Interpretation angegeben:
Ich weiß nicht, ob dies akzeptabel ist, da ich dieses Nachziehen in der Byteanzahl
nb nicht gezählt habe: Es scheint, dass der Interpreter dieses Programm nicht zweimal in der richtigen Reihenfolge ausführen lässt, weil ich die Nummer im Code speichere Weg. Sie müssen es neu laden.
Wie funktioniert das? Der Interpreter folgt den Pfeilen und überspringt eine Anweisung, wenn er '#' überquert.
Graue Punkte sind ein Test, und die rote Linie entfernt nicht benötigte Variablen aus dem Stapel
Mit dem hier im obigen Interpreter angegebenen Code werden die gespeicherten Werte anhand ihrer Darstellungen im Code angezeigt (ich kenne das Format nicht). Ja, Befunge ist eine sehr nachdenkliche Sprache
quelle