Anderer Name: ChessMoveQ
Bestimmen Sie anhand einer Liste mit bis zu 32 Elementen, die jeweils aus 4 Elementen bestehen, und einer zweiten Liste mit 4 Elementen, ob der in der zweiten Eingabe angegebene Zug ein gültiger Schachzug ist.
Die erste Liste zeigt die Position aller 32 Teile auf der Tafel an. Jedes Element folgt der Struktur <colour>, <piece-name>, <x-coord>, <y-coord>
, zum Beispiel ["W", "K", 5, 1]
, die anzeigt, dass der weiße König eingeschaltet ist 5, 1
( e1
auf einem normalen Schachbrett). Alle Elemente der ersten Eingabe sind eindeutig. <x-coord>
und <y-coord>
wird immer zwischen 1 und 8 liegen. Ein Beispiel wäre:
[["B", "K", 3, 8], ["B", "Q", 1, 5], ["B", "N", 4, 7], ["B", "N", 7, 8],
["B", "B", 2, 4], ["B", "R", 4, 8], ["B", "R", 8, 8], ["B", "P", 1, 7],
["B", "P", 2, 7], ["B", "P", 3, 6], ["B", "P", 5, 6], ["B", "P", 6, 7],
["B", "P", 7, 7], ["B", "P", 8, 7], ["W", "K", 5, 1], ["W", "Q", 6, 3],
["W", "N", 3, 3], ["W", "B", 5, 2], ["W", "B", 6, 4], ["W", "R", 1, 1],
["W", "R", 8, 1], ["W", "P", 1, 3], ["W", "P", 2, 2], ["W", "P", 3, 2],
["W", "P", 4, 4], ["W", "P", 6, 2], ["W", "P", 7, 2], ["W", "P", 8, 3]]
welches würde den Vorstand vertreten:
Die zweite Eingabe besteht aus den gleichen Strukturen wie die Unterlisten der ersten, aber anstatt der x- und y-Koordinaten, die angeben, wo sich das Stück befindet, geben sie an, wohin es sich bewegen möchte.
Für das obige Beispiel könnte ein gültiger Zug sein ["W", "B", 4, 3]
(der Bischof bewegt sich ein Feld vorwärts und nach links), und ein ungültiger Zug könnte sein ["B", "R", 4, 1]
, dass der Turm durch den Ritter und den Bauern ziehen müsste, um zum Feld zu gelangen. Als der Umzug in mehrere Stücke zu Zeiten beziehen könnte, müssen Sie prüfen , ob jede der genannten Stücke machen den Umzug, nicht nur einer von ihnen. Zum Beispiel ist das erste Beispiel nur für einen Bischof gültig, aber es ist immer noch ein gültiger Zug. Da jedoch kein schwarzer Turm den zweiten Zug ausführen kann, ist er ungültig.
Ihre Aufgabe ist es festzustellen, ob der in der zweiten Eingabe angegebene Zug ein gültiger Schachzug ist. Die Gültigkeit einer Regel hängt von der Figur ab, die sich zu bewegen versucht (klicken Sie auf den Namen der Figur, um ein Diagramm der gültigen Züge anzuzeigen):
- Jede Figur : Keine Figur kann auf ein bereits belegtes Feld oder von der Tafel gehen, es sei denn, auf diesem Feld befindet sich eine Figur der anderen Farbe. Beispielsweise kann sich eine weiße Figur auf ein Feld bewegen, das von einer schwarzen Figur besetzt ist, jedoch nicht von einer weißen Figur. Außerdem können keine Teile außer Ritter auf Felder verschoben werden, die direkt von einem anderen Teil blockiert werden.
- Eine Bewegung von Teil B zu Quadrat C wird von Teil A "direkt behindert", wenn sich A direkt in einer geraden (orthogonalen oder diagonalen) Linie zwischen B und C befindet .
- Jede Figur : Die Position des Königs kann auch die Gültigkeit des Zuges einer Figur beeinflussen. Wenn eine dieser beiden Bedingungen erfüllt ist, ist die Verschiebung ungültig:
- Setzen Sie den König der Kontrolle aus, indem Sie ein Stück auf die gleiche Seite wie den gefährdeten König bewegen. Dies gilt nur, wenn eine nicht gegnerische Figur den Zug macht, anstatt eine gegnerische Figur, die sich bewegt, um den König in Schach zu setzen.
- Lassen Sie den König in Schach. In diesem Fall muss er außer Kontrolle geraten. Wenn der König in Schach ist und der Zug vorschreibt, dass sich eine andere Figur bewegt, ist dies ein ungültiger Zug, es sei denn, die andere Figur verhindert den Schachzug . Ein Teil kann auf zwei Arten das Prüfen verhindern: Entweder nimmt es das Prüfteil oder es behindert den Weg zwischen dem Prüfteil und dem König.
- Ein "Scheck" ist eine Situation, in der der Gegner des Königs (wenn er an der Reihe wäre) legal eine Figur auf diesen König ziehen könnte. Diese Regel gilt nicht rekursiv, dh ein König ist in Schach, auch wenn der Zug des Gegners auf diesen König seinen eigenen König in Schach lassen würde.
- Bauern : Ein Bauer kann ein Feld vorwärts (dh aufwärts, wenn er weiß ist, abwärts, wenn er schwarz ist) zu einem freien Feld bewegen. Es gibt auch drei spezielle Situationen:
- Wenn sich der Bauer noch nicht bewegt hat (Sie können dies anhand der Y-Koordinate bestimmen; weiße Bauern haben sich nicht bewegt, wenn ihre Y-Koordinate 2 ist, schwarze Bauern haben sich nicht bewegt, wenn ihre Y-Koordinate 7 ist), der Bauer darf zwei Felder vorwärts zu einem freien Feld bewegen.
- Befindet sich eine gegnerische Figur diagonal vor dem Bauern (dh auf dem Feld nordwestlich oder nordöstlich des Bauern, wenn dieser weiß ist, oder südwestlich oder südöstlich, wenn er schwarz ist), der Bauer darf auf das besetzte Feld ziehen.
- Wenn sich ein Bauer in normalen Schachregeln zur letzten Y-Koordinate bewegt (8 für Weiß oder 1 für Schwarz), muss er zu einer Dame, einem Turm, einem Ritter oder einem Bischof derselben Farbe befördert werden. Für die Zwecke dieser Frage spielt die Wahl der Beförderung keine Rolle, ob der Zug gültig ist oder nicht (und kann nicht im Eingabeformat ausgedrückt werden), aber Bauernzüge, die zur Beförderung führen würden, müssen erlaubt sein.
- Bischöfe : Bischöfe können sich zwischen 1 und 8 Feldern entlang eines ununterbrochenen interkardinalen (dh diagonalen) Pfades bewegen.
- Ritter : Ritter können sich in einer
L
Formbewegen, die aus folgenden (äquivalenten) Zügen besteht:- Ein einzelnes Feld in einer beliebigen Himmelsrichtung, gefolgt von einer 90/270 ° -Drehung, gefolgt von einer letzten Bewegung von 2 Feldern vorwärts.
- 2 Felder in einer beliebigen Himmelsrichtung, gefolgt von einer 90/270 ° -Drehung, gefolgt von einer letzten Bewegung eines einzelnen Feldes vorwärts.
- Türme : Türme können sich zwischen 1 und 8 Feldern entlang eines ununterbrochenen Kardinalpfades bewegen.
- Königinnen : Königinnen können sich zwischen 1 und 8 Feldern entlang eines durchgehenden kardinalen oder interkardinalen (dh diagonalen) ungehinderten Pfades bewegen.
- Könige : Könige bewegen sich wie Königinnen, mit der Ausnahme, dass sie nur ein Feld pro Zug bewegen dürfen (dh ein König kann sich nur auf kardinal oder diagonal benachbarte Felder bewegen). Zur Erinnerung, Sie können keinen Zug machen, der Ihren König in Schach hält. Sie können also auch Ihren König nicht in Schach setzen.
Die Schachregeln enthalten auch spezielle Züge, die "Rochade" und "en passant" genannt werden. Da die Rechtmäßigkeit dieser Züge jedoch von der Geschichte des Spiels abhängt, nicht nur von der aktuellen Position (und da beim Rochieren zwei Stücke gleichzeitig verschoben werden müssen, was nicht zum Eingabeformat passt), sollten Sie keinen dieser Züge in Betracht ziehen zu existieren (dh ein Umzug, der Rochade oder en passant wäre, sollte als illegal angesehen werden).
Sie können zwei unterschiedliche Ergebnisse ausgeben, um die Gültigkeit eines Zuges anzuzeigen, und Sie können Eingaben in eine von Ihnen gewünschte Methode vornehmen. Sie können auch 0-Indizierung anstelle von 1-Indizierung für die Positionen wählen, wenn Sie dies vorziehen. Dies ist ein Code-Golf , also gewinnt der kürzeste Code!
Testfälle
Board
Move => Output (Reason)
[["B", "K", 3, 8], ["B", "Q", 1, 5], ["B", "N", 4, 7], ["B", "N", 7, 8], ["B", "B", 2, 4], ["B", "R", 4, 8], ["B", "R", 8, 8], ["B", "P", 1, 7], ["B", "P", 2, 7], ["B", "P", 3, 6], ["B", "P", 5, 6], ["B", "P", 6, 7], ["B", "P", 7, 7], ["B", "P", 8, 7], ["W", "K", 5, 1], ["W", "Q", 6, 3], ["W", "N", 3, 3], ["W", "B", 5, 2], ["W", "B", 6, 4], ["W", "R", 1, 1], ["W", "R", 8, 1], ["W", "P", 1, 3], ["W", "P", 2, 2], ["W", "P", 3, 2], ["W", "P", 4, 4], ["W", "P", 6, 2], ["W", "P", 7, 2], ["W", "P", 8, 3]]
["W", "R", 8, 2] => True (The rook on h1 can move forward one)
[['B', 'K', 6, 8], ['B', 'Q', 1, 7], ['B', 'N', 1, 3], ['B', 'N', 7, 1], ['B', 'B', 8, 8], ['B', 'B', 2, 5], ['B', 'R', 4, 3], ['B', 'R', 1, 5], ['B', 'P', 5, 5], ['B', 'P', 7, 2], ['B', 'P', 5, 7], ['B', 'P', 5, 6], ['B', 'P', 4, 4], ['W', 'K', 7, 3], ['W', 'Q', 3, 2], ['W', 'N', 4, 8], ['W', 'N', 7, 5], ['W', 'B', 1, 1], ['W', 'B', 8, 1], ['W', 'R', 1, 8], ['W', 'R', 3, 7], ['W', 'P', 8, 2], ['W', 'P', 6, 3], ['W', 'P', 4, 2], ['W', 'P', 1, 4], ['W', 'P', 8, 7]]
['W', 'N', 1, 5] => False (Neither knight to move to a5 from where they are)
[['B', 'K', 7, 3], ['B', 'Q', 2, 4], ['B', 'N', 5, 2], ['B', 'N', 1, 6], ['B', 'B', 7, 7], ['B', 'B', 1, 8], ['W', 'K', 7, 1], ['W', 'Q', 6, 1], ['W', 'N', 5, 6], ['W', 'N', 3, 3], ['W', 'B', 2, 2], ['W', 'B', 6, 5]]
['B', 'K', 8, 3] => False (The white bishop would put the king in check)
[['B', 'K', 7, 6], ['B', 'Q', 8, 3], ['B', 'N', 7, 7], ['B', 'N', 8, 7], ['B', 'B', 2, 2], ['B', 'B', 3, 8], ['B', 'R', 1, 1], ['B', 'R', 1, 6], ['B', 'P', 8, 5], ['B', 'P', 4, 3], ['B', 'P', 8, 6], ['W', 'K', 7, 8], ['W', 'Q', 7, 2], ['W', 'N', 5, 1], ['W', 'N', 4, 6], ['W', 'B', 1, 2], ['W', 'B', 2, 6], ['W', 'R', 4, 4], ['W', 'R', 3, 6], ['W', 'P', 5, 2], ['W', 'P', 6, 2]]
['B', 'N', 5, 8] => False (The white queen currently has the king in check, and this move doesn't prevent that)
[['B', 'K', 7, 6], ['B', 'Q', 8, 3], ['B', 'N', 7, 7], ['B', 'N', 8, 7], ['B', 'B', 2, 2], ['B', 'B', 3, 8], ['B', 'R', 1, 1], ['B', 'R', 1, 6], ['B', 'P', 8, 5], ['B', 'P', 4, 3], ['B', 'P', 8, 6], ['W', 'K', 7, 8], ['W', 'Q', 7, 2], ['W', 'N', 5, 1], ['W', 'N', 4, 6], ['W', 'B', 1, 2], ['W', 'B', 2, 6], ['W', 'R', 4, 4], ['W', 'R', 3, 6], ['W', 'P', 5, 2], ['W', 'P', 6, 2]]
['B', 'N', 7, 5] => True (The king is in check, and the knight blocks that)
[['B', 'K', 8, 3], ['B', 'Q', 6, 5], ['B', 'N', 7, 8], ['B', 'N', 3, 7], ['B', 'B', 4, 1], ['B', 'B', 1, 1], ['W', 'K', 7, 7], ['W', 'Q', 7, 1], ['W', 'N', 2, 2], ['W', 'N', 1, 3], ['W', 'B', 3, 5]]
['B', 'B', 2, 2] => True (takes the white knight)
[['B', 'K', 6, 1], ['B', 'Q', 6, 2], ['W', 'K', 8, 1]]
['B', 'Q', 7, 1] => True (Smallest checkmate possible, in terms of bounding box)
Diese Herausforderung war Sandkasten . Da es ohne jede Erklärung Abwertungen erhielt, beschloss ich, es trotzdem zu posten
quelle
Antworten:
Python 2 (mit Python-Schach ),
141 138 134 133132 BytesOhne irgendeinen der wirklich interessanten Codes zu machen - aber kann dies vielleicht mit Golfsprachen oder (wage ich es zu erwähnen) Mathematica konkurrieren?
Hinweis: python-Schach ist ein PyPI Paket auf Python installiert 2.7.9+ mit:
python -m pip install python-chess
)Ein vollständiges Programm, das die Eingabe von drei Elementen akzeptiert:
PRNBQK
)a1
ist0
,b1
ist1
, ...a2
ist8
, ...,h8
ist63
,Das Programm gibt über seinen Exit-Code bei gültiger Eingabe aus:
1
wenn der Zug gültig ist (das Programm hat einen Fehler ausgelöst - aufgrund der Division durch Null);0
es ist es nicht (das Programm wird normal beendet)(Nicht) Online ausprobieren! (Da das Python-Chess-Paket dort nicht installiert ist und TIO keine Internetverbindung zulässt, funktioniert der PIP-Installationscode im Header nicht.)
Beachten Sie, dass das Netzbetreiber in Python macht
1**1 == 1**0 == 0**0 == 1
aber0**1 == 0
... also
1/0**1
wirft eine Division durch Null - Fehler während1/1**1
,1/1**0
und1/0**0
alle Erfolg haben(... und das in Python
False
undTrue
Equate zu0
und1
respectively).quelle
str(S.piece_at(m.from_square))==p for
zup==str(S.piece_at(m.from_square))for
, dass ein Byte speichern sollte.repr
Backticks, die ich ersetzen wolltestr
, auswerten kann, um zu sparen ...Regex (PCRE2),
931925837 BytesDiese Lösung weicht von der Problemstellung dahingehend ab, dass anstelle eines Board-Status und eines Move zwei Board-Status an den regulären Ausdruck übergeben werden. Die Bewegung wird aus der Differenz zwischen den beiden Board-Zuständen abgeleitet. Deshalb habe ich es mir zur Aufgabe gemacht, die Testfälle in dem von dieser Frage vorgegebenen Format zu erstellen, alle Instanzen des beschriebenen Stücks auf der Tafel zu finden und mit jedem einzelnen zu versuchen, es an die Zielposition zu bewegen und den regulären Ausdruck auszuwerten mit dieser Möglichkeit herauszufinden, ob irgendwelche vom regulären Ausdruck als gültig gemeldet werden. Wenn das nicht in Ordnung ist, lass es mich wissen. Es ist möglich, einen regulären Ausdruck als Position + Verschiebung zu implementieren, dies wäre jedoch weniger elegant und erfordert eine ernsthafte Umgestaltung.
Die Tafel wird in 8 × 8 ASCII dargestellt, wobei weiße Teile in Großbuchstaben und schwarze in Kleinbuchstaben geschrieben sind: P awn, k N ight, B ishop, R ook, Q ueen, K Ing. Die schwarze Seite (Rang 8) liegt oben und die weiße Seite (Rang 1) unten. Jeder Rang wird durch eine neue Linie getrennt und leere Felder werden als markiert
-
. Die beiden Boardpositionen sind durch einen zusätzlichen Zeilenumbruch getrennt.Das eigentliche Ziel dieses Projekts ist die Validierung ganzer Spiele, nicht nur einzelner Züge. Weiter unten finden Sie Informationen zum aktuellen Status.
Probieren Sie es online!
Hübsch gedruckt und teilweise ungolfed (die absoluten Rückreferenzen wurden in relative und die Erfassungsgruppen in nicht erfassende oder in einigen Fällen aus Gründen der Geschwindigkeit atomare Gruppen geändert):
-88 Bytes durch Verwendung von nichtatomaren Unterprogrammaufrufen, wodurch ein erneutes Targeting von PCRE1 nach PCRE2 erfolgt
Die obige Version wurde modifiziert, um weder En passant noch Castling zuzulassen, aber das gesamte Projekt befindet sich derzeit in einem Zustand, in dem alle Arten von Zügen validiert werden, beginnend mit dem anfänglichen Board-Status (der die Standard-Schach-Startposition sein muss - Chess960 nicht) unterstützt, aber zumindest). Die vollständigen Regeln von en passant und castling werden eingehalten.
Hier ist ein Beispielspiel, das von der vollständigen Regex validiert wurde (PCRE1 - noch nicht neu ausgerichtet) [regex101.com] .
Ein ungültiger Zug führt dazu, dass jede nachfolgende Brettposition nicht übereinstimmt / hervorgehoben wird. Die Schachmatt- / Patt-Erkennung und damit die Erkennung, wer der Gewinner ist (oder ob es sich um ein Unentschieden handelt), ist noch nicht implementiert. Aus diesem Grund wird der endgültige Board-Status in diesem Beispiel nicht hervorgehoben.
Hier ist ein C / C ++ - Programm, das die algebraische Notation in das von dieser Regex erkannte Format konvertiert.Die algebraische Notation muss derzeit in Form eines Arrays in den Quellcode eingefügt werden, mit separaten Zeichenfolgen für jede Verschiebung, aber als einzelne Zeichenfolge aus stdin oder einem Befehlszeilenargument, wobei die gesamte Sequenz von Verschiebungen durch Leerzeichen getrennt ist und Punkt-terminierte Zugnummern sind geplant.
Ich habe auch mit einem regulären Ausdruck begonnen, der eine vollständige Partie rein in algebraischer Schachnotation validiert, wobei die Standardausgangsposition impliziert ist. Alles, was es braucht, ist ein leeres "Rubbellos", das am Ende der Eingabe angehängt wird (nach der Liste der Züge). Ich bin mir ziemlich sicher, dass es möglich ist, dies vollständig umzusetzen und es irgendwann fertigzustellen.
quelle