Magic Box Problem

15

Sie haben ein Eingabearray der Größe m * n. Jede Zelle im Array wird entweder mit P oder T gefüllt. Die einzige Operation, die Sie für das Array ausführen können, ist das Umblättern von Spalten. Wenn Sie eine Spalte spiegeln, wechseln die Buchstaben in allen Zellen dieser Spalte (P wird zu T und umgekehrt). Wenn Sie eine 'x'-Anzahl von Zeilen mit demselben Buchstaben haben (z. B. PPPP), erhalten Sie einen Punkt. Entwerfen Sie einen Algorithmus, der das Array aufnimmt und eine Lösung (welche Spalten gespiegelt werden sollen) zurückgibt, sodass das resultierende Array die maximal mögliche Anzahl von Punkten aufweist.

Hinweis: Falls es mehrere Lösungen gibt, die die höchste Punktzahl erzielen, wählen Sie die mit der niedrigsten Anzahl von Flips. Beispiel:

Eingangsarray:

PPTPP
PPTPP
PPTTP
PPPTT
PPPTT

Ausgabe:

3

Erläuterung:
Eine Lösung, die die höchsten Punkte liefert: Spalte Nr. 3
Dann wäre das ursprüngliche Array:

PPPPP // 1 point
PPPPP // 1 point
PPPTP
PPTTT
PPTTT

//Total: 2 points

Beachten Sie, dass Sie auch die Spalten 4 und 5 spiegeln können, um eine Punktzahl von zwei zu erhalten, dies erfordert jedoch einen zusätzlichen Flip.

Sie können jedes geeignete Eingabeformat verwenden, um das zweidimensionale Array darzustellen, und Sie können auch zwei unterschiedliche, aber feste Werte verwenden, um Pund darzustellen T.

Dies ist Codegolf, daher gewinnt die kürzeste Antwort (in Bytes).

bruhhhhh
quelle
6
Willkommen bei PPCG. Dies ist eine große Herausforderung, aber es braucht ein Erfolgskriterium, um über das Thema zu sprechen.
Ypnypn
Kann ich das Eingabeformat steuern? Kann ich sagen, dass P falsch und T wahr ist? Wenn nicht, wie lautet das Eingabeformat?
stolzer Haskeller
Klar, das Eingabeformat spielt keine Rolle. Angenommen, Sie haben ein Array von Zeichen, Ints oder Booleschen Zeichen in zwei Richtungen oder einen beliebigen Typ.
Frühhhhh
3
Sie benötigen ein Gewinnkriterium, um zu entscheiden, welche der gültigen Antworten die beste ist. Unter der Annahme, dass eine gültige Antwort die maximalen Punkte für das Eingaberaster ergeben muss (Übrigens sollten Sie dies angeben), sollte es möglich sein, ein 32-Spalten-Raster in angemessener Zeit zu erzwingen. Daher schlage ich vor, Sie machen ua Codegolf (kürzeste Code-Gewinne)
Level River St
1
Ich habe in Peters erstem Vorschlag gearbeitet. Fühlen Sie sich frei, die Formulierung zu ändern, wenn Sie es nicht mögen.
Martin Ender

Antworten:

3

APL, 37

{x/1+⍳⍴x←y[↑⍋(+/∘.≠⍨2⊥⍉y),¨+/y←⍵⍪~⍵]}

Beispiel:

{x/1+⍳⍴x←y[↑⍋(+/∘.≠⍨2⊥⍉y),¨+/y←⍵⍪~⍵]} 5 5⍴0 0 1 0 0 0 0 1 0 0 0 0 1 1 0 0 0 0 1 1 0 0 0 1 1

Hier getestet.

jimmy23013
quelle
1

Pyth , 28

f@eo+/QN/Qm!dN_osZ^U2lhQTUhQ

Nimmt Eingaben in Form einer verschachtelten Liste vor, z

[[0,0,1,0,0],[0,0,1,0,0],[0,0,1,1,0],[0,0,0,1,1],[0,0,0,1,1]]

Gibt den Ausgang 0-indiziert aus, z

[2]

^U2lhQ: Erzeugt alle möglichen Listen von Nullen und Einsen mit der richtigen Länge.

_osZ: Ordnet diese Listen von den meisten Einsen bis zu den wenigsten an.

+/QN/Qm!dN: Zählt, wie oft jede Liste ( N) und ihre Umkehrung, vertauschte 0s und 1s ( m!dN) in der Eingabe auftreten. Ersteres entspricht einer Reihe von Flips, bei denen alle Nullen und bei letzteren alle Einsen übrig bleiben.

eo: Ordnet die Liste nach dem obigen Schlüssel und nimmt das letzte Element, das das Ergebnis mit den am besten übereinstimmenden Spalten ist, und darunter das mit den am wenigsten übereinstimmenden.

f@ ... TUhQ: Konvertiert diese Liste der Einsen und Nullen in eine Liste der zu spiegelnden Indizes.

Ändern Sie für die 1-Indizierung den Wert din a kund setzen Sie ihn dann mhdan den Anfang.

isaacg
quelle
0

CJam, 53 51 Bytes

l~z:X,,La\{1$f++}/{,}${X\{_X=:!t}/z{_&,(},,}$0=:)S*

Dies liest ein zweidimensionales Array von 0s und 1s aus STDIN. ZB wäre das Beispiel in der Frage

[[0 0 1 0 0] [0 0 1 0 0] [0 0 1 1 0] [0 0 0 1 1] [0 0 0 1 1]]

Teste es hier.

Hiermit werden zunächst alle möglichen Teilmengen von Spalten in aufsteigender Reihenfolge abgerufen, dann die Kippvorgänge für jede Teilmenge ausgeführt und nach der Anzahl der Zeilen sortiert, in denen sich noch sowohl Nullen als auch Einsen befinden. Schließlich geben wir nur die erste solche Teilmenge zurück. Dies setzt voraus, dass die Sortierung stabil ist, so dass die anfängliche Reihenfolge mit zunehmender Länge für den Kabelbinder sorgt.

Martin Ender
quelle
0

Haskell, 98

g s=snd$maximum[((sum[1|o<-s,o==r||o==map(1-)r],-sum r),[i|(i,1)<-zip[1..]r])|r<-s++map(map(1-))s]

Das Eingabeformat ist eine Liste mit Ints. Sie können eine String-Version zum Testen verwenden:

gg = g . map (map (\c -> case c of 'T' -> 0 ; _ -> 1) ) . lines

oh nein die Räume! es tut weh!

Dies funktioniert, indem wir die Zeilen durchlaufen und die Anzahl der Punkte berechnen, die wir erhalten, wenn wir die Spalten so spiegeln, dass diese Zeile uns einen Punkt einbringt.

Als erstes ist zu bemerken, dass das Umkehren der Zeile in alle Trueoder alle Falsekeine Rolle spielt, da die Gitter genau umgekehrt zueinander sind und daher genau die gleiche Punktzahl haben.

Die Art und Weise, wie wir die Anzahl berechnen, wenn eine bestimmte Zeile einen Punkt erhält, ist wie folgt: Wir iterieren erneut über die Zeilen und addieren die Punkte, die jede Zeile uns gibt, wobei wir die Tatsache zugrunde legen, dass sie genau dann funktionieren, wenn die Zeilen entweder identisch oder genau umgekehrt sind.

Wenn zum Beispiel die Zeile, die wir umdrehen, TPPTPund die aktuelle Zeile, über die wir iterieren, ist PTTPToder TPPTPdie Zeile uns einen Punkt einbringt , aber wenn es sich um eine andere Zeile handelt, erhält sie uns keine Punkte.

stolzer haskeller
quelle
@ MartinBüttner Ja, ich werde es in Kürze beheben (hoffentlich)
stolzer Haskeller
0

CJam, 37

q~_{:!}%+:T{T1$a-,\0-+}$0={U):U*}%0-`

Eingabeformat:

[[0 0 1 0 0] [0 0 1 0 0] [0 0 1 1 0] [0 0 0 1 1] [0 0 0 1 1]]
jimmy23013
quelle
0

Python 2, 234

from itertools import *
A=input()
n=len(A[0])
R=range(n)
S=(0,)
for p in[q for i in R[:-1] for q in combinations(R,i)]:
    s=[sum([(l[q]+(q in p))%2 for q in R])for l in A]
    m=s.count(n)+s.count(0)
    if m>S[0]:S=(m,p)
print S[1]

Die Eingabe ist eine Liste von Listen:

[[0,0,1,0,0],[0,0,1,0,0],[0,0,1,1,0],[0,0,0,1,1],[0,0,0,1,1]]

Die Ausgabe ist ein Tupel von Flips mit Python-Indizierung von 0:

(2,)

Wenn die Ausgabe von 1 indexiert werden muss, besteht der Code aus 272 Zeichen, wobei 0 bedeutet, dass keine Umkehrungen vorhanden sind:

print 0 if len(S[1])==0 else [p+1 for p in S[1]]
user2487951
quelle