Ein lateinisches Quadrat ist ein Quadrat , das keine Symbole in den Zeilen oder Spalten wiederholt hat: .
13420
21304
32041
04213
40132
Und wie viele Sudoku-Spieler wissen, brauchen Sie nicht alle Zahlen, um die verbleibenden Zahlen abzuleiten.
Ihre Herausforderung besteht darin, ein lateinisches Quadrat in so wenige Bytes wie möglich zu komprimieren. Sie müssen ein oder zwei Programme bereitstellen, die komprimiert / dekomprimiert werden.
Verschiedene Infos:
- Die verwendeten Zahlen sind immer
0..N-1
, woN
ist die Länge der Kante des Quadrats, undN<=25
- Bei der Dekomprimierung muss das lateinische Quadrat mit der Eingabe identisch sein.
- Ihre Programme sollten in der Lage sein, alle lateinischen Quadrate (innerhalb der maximalen Quadratgröße) zu (de) komprimieren , nicht nur die, die ich bereitgestellt habe. Das Kompressionsverhältnis sollte ebenfalls ähnlich sein.
- Sie müssen die Komprimierung und Dekomprimierung tatsächlich ausführen, um Ihre Punktzahl zu erhalten (keine Laufzeit am Ende des Universums).
Die Testfälle sind auf Github zu finden . Ihre Punktzahl ist die Gesamtgröße der komprimierten Testfälle.
BEARBEITEN: Ab 20:07 Uhr am 7. Juli habe ich die Testfälle aktualisiert (um ein Generationsproblem zu beheben). Bitte führen Sie Ihr Programm für die neuen Testfälle erneut aus. Danke Anders Kaseorg .
code-challenge
compression
Nathan Merrill
quelle
quelle
0
obwohln-1
:)n
verschiedene Symbole verwenden. : PAntworten:
Python,
1281,375,1268,625 BytesWir codieren das lateinische Quadrat nacheinander als "Entscheidung", wobei jede Entscheidung eine der drei folgenden Formen hat:
Bei jedem Schritt treffen wir alle logischen Schlussfolgerungen, die wir aus früheren Entscheidungen ziehen können, und wählen dann die Entscheidung mit der geringstmöglichen Anzahl von Auswahlmöglichkeiten aus, die daher die geringste Anzahl von Bits zur Darstellung benötigen.
Die Auswahlmöglichkeiten werden von einem einfachen arithmetischen Decoder bereitgestellt (div / mod durch die Anzahl der Auswahlmöglichkeiten). Die Kodierung bleibt jedoch etwas redundant: Wenn k zu einem Quadrat dekodiert, bei dem das Produkt aller Auswahlen m war , dann dekodieren k + m , k + 2⋅ m , k + 3⋅ m ,… zu demselben Quadrat mit etwas Restzustand am Ende.
Wir nutzen diese Redundanz, um die Größe des Quadrats nicht explizit zu codieren. Der Dekomprimierer beginnt mit dem Versuch, ein Quadrat der Größe 1 zu dekodieren. Wenn der Dekodierer mit dem Reststatus fertig ist, wirft er dieses Ergebnis aus, subtrahiert m von der ursprünglichen Zahl, erhöht die Größe um 1 und versucht es erneut.
Ausgabe:
quelle
np.stack()
. In diesem Fall kann es durch ersetzt werdennp.array([…])
, und das habe ich in der aktuellen Version getan.MATLAB,
3'062.52'888.125 BytesBei diesem Ansatz werden nur die letzte Zeile und die letzte Spalte des Quadrats getrennt und jeder Eintrag in Wörter mit einer bestimmten Bittiefe konvertiert. Die Bittiefe wird für das gegebene Größenquadrat minimal gewählt. (Vorschlag von @KarlNapf) Diese Wörter werden nur aneinander angehängt. Dekompression ist genau das Gegenteil.
Die Summe aller Testfälle beträgt 23'105 Bits oder 2'888.125 Bytes. (Gilt immer noch für die aktualisierten Testfälle, da die Größe meiner Ausgaben nur von der Größe der Eingabe abhängt.)
quelle
n=9..16
4 Bits ausreichen.Python 3, 10772 Bit (1346,5 Byte)
Das Komprimieren und Dekomprimieren der kombinierten Testfälle dauert 0,1 Sekunden.
Überprüfen Sie die Punktzahl auf Ideone .
quelle
len(possible)
ist 1 undpossible.index(rows[i][j])
ist 0 , so dass Symbol ohne Kosten codiert wird.J , 2444 Bytes
Verlässt sich beim
A.
Konvertieren in und aus einer Permutation von Ganzzahlen [0, n) und einem Permutationsindex auf das integrierte Element .Komprimieren Sie 36 Byte
Die Eingabe ist ein 2D-Array, das das lateinische Quadrat darstellt. Jede Zeile wird in einen Permutationsindex konvertiert, und dieser Index wird in eine Liste mit Basis-255-Stellen konvertiert und durch einen ASCII-Wert ersetzt. Jede Zeichenfolge wird dann mit dem ASCII-Zeichen bei 255 verbunden.
Dekomprimieren Sie 45 Byte
Teilt die Eingabezeichenfolge bei jedem ASCII-Wert von 255 auf und parst jede Gruppe als 255-stellige Basis. Erstellen Sie dann unter Verwendung der Anzahl der Gruppen eine Liste von Ganzzahlen [0, Länge] und permutieren Sie sie entsprechend jedem Index und geben Sie sie als 2d-Array zurück.
quelle
Python,
605245213556 Bytescompress
Nimmt das Quadrat wie in den Beispielen als mehrzeilige Zeichenfolge und gibt eine binäre Zeichenfolge zurück, wohingegendecompress
das Gegenteil der Fall ist.Entfernen Sie die letzte Reihe + Spalte und machen Sie den Rest Reißverschluss zu.
base64
scheint nicht nötigquelle
Python 3, 1955 Bytes
Noch eine, die Permutationsindizes verwendet ...
Ausgabe
quelle
Python3 -
3.572 3.581BytesdataCompress
Nimmt eine Liste von Integer-Tupeln und gibt einen String zurück.dateDeCompress
Nimmt einen String und gibt eine Liste von Integer-Tupeln zurück.Kurz gesagt, für jede Zeile nimmt dieses Programm den Permutationsindex dieser Zeile und speichert ihn in Basis 36. Das Dekomprimieren dauert bei großen Eingaben sehr lange, aber die Komprimierung ist selbst bei großen Eingaben sehr schnell.
Verwendung:
dataCompress([(2,0,1),(1,2,0),(0,1,2)])
Ergebnis:
c|4|3|0
dataDeCompress("c|4|3|0")
Ergebnis:
[(2, 0, 1), (1, 2, 0), (0, 1, 2)]
quelle
permutations
Anrufe nicht inlist
Anrufepermutations
einbinden würden - Sie erhalten einen Generator, der träge alle Permutationen generiert, aber wenn Sie versuchen, daraus eine zu machenlist
, werden eifrig alle Permutationen generiert, die benötigt werden eine sehr lange Zeit.O(n)
, anstatt nach demO(n!)
Brute-Force-Ansatz, bei dem alle Permutationen überprüft werden .Java, 2310 Bytes
Wir konvertieren jede Zeile des Quadrats in eine Zahl, die angibt, für welche lexikographische Permutation faktoradische Zahlen verwendet werden, die auch als faktorielles Zahlensystem bezeichnet werden und zum Nummerieren von Permutationen nützlich sind.
Wir schreiben das Quadrat in eine Binärdatei, wobei das erste Byte die Größe des Quadrats hat, und dann hat jede Zeile ein Byte für die Anzahl der Bytes in der Binärdarstellung einer Java-BigInteger, gefolgt von den Bytes dieser BigInteger.
Um den Prozess umzukehren und das Quadrat zu dekomprimieren, lesen wir zuerst die Größe und dann jede BigInteger und verwenden diese Zahl, um jede Zeile des Quadrats zu generieren.
Permutor wurde aus einer Klasse, die ich vor einigen Jahren geschrieben habe, angepasst, um mit Permutationen zu arbeiten:
Verwendung:
Mit einem lateinischen Quadrat in
latin.txt
komprimieren Sie es:Und dekomprimiere es:
quelle