Symuluj obracanie tablicy


14

Wprowadzenie

Grasz w pasującą grę, w której monety są wkładane u góry i opadają na dno (na górną monetę) z powodu grawitacji.

Więc to

O <- inserting this coin

OO O
OOOOO

stanie się tym

O
OO O
OOOOO

Teraz wyobraź sobie, że ktoś obraca tablicę zgodnie z ruchem wskazówek zegara. Staną się następujące zdarzenia:

1. Tablica jest obrócona

OOO
OO
O
OO
O

2. Monety spadają z powodu grawitacji

O
O
OO
OO
OOO

Twoje zadanie

Twoim zadaniem jest symulacja obrotu tablicy, pisząc program lub funkcję. Dla uproszczenia mamy do czynienia tylko z jednym rodzajem monety (nie jest to zbyt ekscytująca gra polegająca na dopasowywaniu, prawda?). Możesz założyć, że grawitacja jest stosowana dopiero po zakończeniu obrotu. Płyta jest obracana zgodnie z ruchem wskazówek zegara.

Wejście

Dane wejściowe będą ciągiem znaków, który zawiera 3 typy znaków:

  • O (kapitał o) LUB 0 (zero) - moneta (Ty decydujesz, które obsługuje Twoje rozwiązanie)
  • (spacja) - puste pole
  • \ n (nowa linia) - koniec wiersza

Dane wejściowe reprezentują stan płyty. Możesz założyć, że dane wejściowe są dobrze uformowane i zawierają prawidłowy stan planszy (nie płyną żadne monety). Wejście może być parametrem funkcji lub może być odczytane ze standardowego wejścia lub z pliku.

Wynik

Wyjście to nowy stan płytki po obrocie. Dane wyjściowe zawierają te same 3 typy znaków co dane wejściowe. Dane wyjściowe mogą zostać zwrócone z funkcji lub zapisane na standardowym wyjściu lub w pliku.

Próba

Wejście 1:

O
OO O
OOOOO

Wyjście 1:

O
O
OO
OO
OOO

Input2:

O O
O O

Wyjście 2:

OO
OO

Możesz użyć dowolnego języka i standardowej biblioteki wybranego języka. Najkrótszy program w bajtach wygrywa.


Czy krótsze linie są wypełnione spacjami?
— Ventero

Jeśli potrzebujesz, to tak.
— David Frank

Jakie są wymagania dotyczące rozmiaru płyty? Czy mogę wybrać rozsądny maksymalny rozmiar, czy aplikacja / funkcja musi działać dla wszystkich możliwych rozmiarów?
— Fors

2
Jeśli grawitacja zostanie zastosowana po obrocie, w jaki sposób Input2 staje się Output2? Myślałem, że spadnie górne monety w dół, ale nie poziomo?
— Matt

2
@Matt Zauważ, że nie ma pustych wierszy na Input2, ani na Output2 (SE wyświetla margines między wierszami).
— David Frank

Odpowiedzi:


16

GolfScript, 14 12 znaków

' '-n%zip$n*

Dane wejściowe należy podać na STDIN, znakiem dla monet mogą być dowolne znaki spacje. Spróbuj tutaj . Dzięki Peterowi za zwrócenie uwagi na redukcję dwóch postaci.


Och, czego bym nie dał za transposeRuby, które poradzi sobie z tablicami o różnych długościach ...
— Ventero

@Ventero Większość czasu używam tego hacky wersję: ([nil]*a.map(&:size).max).zip(*a). Nie nadaje się do gry w golfa.
— Howard

Można zapisać 2 znaków: ponieważ najdłuższe linie zawsze kończy się na dole, można zastąpić -1%z $.
— Peter Taylor

@PeterTaylor Masz rację - możemy zapisywać znaki. Dziękuję Ci.
— Howard

1
@PeterTaylor Cóż, dodałem alias jednoznakowy dla " ".
— Aditsu zrezygnowało, ponieważ SE ma EVIL

6

JavaScript (E6) 103

Pierwsza próba, tylko operacje na macierzach. Każdy wiersz w ciągu wejściowym musi być wypełniony.
Całkiem niewygodny.

R=t=>(x=t.split('\n').reverse().map(x=>[...x].sort()),x.map((c,i)=>x.map(r=>r[i]).join('')).join('\n'))

Pseudo kod

  1. string -> tablica wierszy
  2. odwrotna tablica góra / dół
  3. każdy wiersz -> tablica znaków
  4. posortuj każdy rząd (monety „spadają” w prawo)
  5. transponować
  6. każda tablica znaków w rzędzie -> ciąg
  7. łączyć tablicę -> pojedynczy ciąg

O rany, sortowanie jest sprytne (+1)! Czy mogę to ukraść?
— patrz

Nigdy wcześniej nie widziałem tej składni [...x]. Jak to jest nazywane?
— ComFreek


2
@ edc65 Złamałeś własny link w nawiasach. Oto poprawny link
— Chris Cirefice

6

Ruby 2.0, 59 znaków

puts$<.map(&:chars).reverse.transpose.sort[1,50].map &:join

Wejście przez stdin, zakłada, że ​​wszystkie linie mają tę samą długość. Jest to prawdopodobnie znacznie dłużej niż to konieczne. Ale przynajmniej jest czytelny ...


Myślę, że możesz $<.mapzamiast tego użyć .
— Howard

@ Howard To jedna rzecz, o której zawsze zapominam. Dzięki!
— Ventero

1
co tam robi [1,50]?
— Nie to, że Charles

1
@Charles Pomija pierwszy wiersz, który zawiera wszystkie nowe wiersze z wejścia. David wspomniał w komentarzu, że 50 x 50 jest maksymalnym możliwym rozmiarem, więc zamiast wybierać wszystkie oprócz pierwszego wiersza ( 1..-1), po prostu wybieram 50 wierszy, zaczynając od drugiego ( 1,50).
— Ventero

@Ventero ma to. chłodny. dzięki!
— Nie to, że Charles

3

J - 49 31 24 bajtów

Myślę, że mogą tam występować niepotrzebne obroty, ale w przeciwnym razie działa dobrze. Jest to funkcja, która pobiera dane wejściowe zgodnie z opisem, monety są O. Wejście nie wymaga spacji końcowych.

Nowa wersja, zainspirowana odpowiedzią JavaScript edc65 :

f=:[:|."1@|:[:/:~"1,;._2

Wyjaśnienie:

f=:[:|."1@|:[:/:~"1,;._2
                   ,;._2 Split the string at every fret, which is the last character in the string (newline).
              /:~"1      Sort every row separately.
     |."1@|:             Rotate the array clockwise.

Stara wersja:

f=:[:|:((#~=&' '),=&'O'#])"1@|:@(|."1@|:)@(,;._2)

Wyjaśnienie:

f=:[:|:((#~=&' '),=&'O'#])"1@|:@(|."1@|:)@(,;._2)
                                          (,;._2) Split the string at every fret, which is the last character in the string (newline).
                                (|."1@|:)@        Rotate the array clockwise.
                             |:@                  Reverse the axes (columns become rows and vice-versa).
       ((#~=&' '),=&'O'#])"1                      Function that applies the "gravity"
                          "1                       Apply to every row separately:
                  =&'O'#]                           Get the O's in the row.
       (#~=&' ')                                    Get the spaces in the row.
                ,                                   Join them, spaces come first.
  [:|:                                            Reverse axes again.

Przykłady (zauważ, że ciągi wielowierszowe zaczynają się 0 : 0i kończą na nawiasie):

   f 0 : 0
O
OO O
OOOOO
) NB. output starts now
O  
O  
OO 
OO 
OOO
   f 0 : 0
O O
O O
) NB. Output starts now.

OO
OO

Jeśli możesz, posortuj przed obróceniem
— edc65

@ edc65 Jesteś mądrym człowiekiem.
— patrz

2

Haskell - 86

Właśnie się uczę, więc jestem pewien, że można to poprawić.

import Data.List
c=putStr.unlines.filter(/="").sort.map(filter(/=' ')).transpose.lines

Przykładowe dane wejściowe:

let a = "O    \nOO O \nOOOOO"
let b = " O O \n O O "
c a
c b

Przykładowe dane wyjściowe:

O
O
OO
OO
OOO

OO
OO

2

Python 2 (69) (79)

for c in sorted(zip(*raw_input().split("\\n"))):print''.join(c[::-1])

Pobiera dane wypełnione spacjami, aby wszystkie linie miały jednakową długość. splitTworzy arrat każdej linii. zipSkutecznie transpozycję macierzy. Następnie sortedsortuje krotki w porządku leksykograficznym, powodując, że wszystkie monety spadają na dno. Na koniec drukujemy każdą linię, zamieniając ją z powrotem w ciąg znaków, jednak najpierw musimy ją odwrócić. Działanie print'O'*c.count('O')jest równoważne i wykorzystuje tę samą liczbę znaków.

Przykładowy przebieg:

>> O    \nOO O \nOOOOO
O
O
OO
OO
OOO

1

C, 167 119 bajtów

Ta krótsza wersja jest (niestety?) Znacznie bardziej przejrzysta niż oryginał.

m;j;b[99];r;main(){while(j=getchar()+1)j-11?m+=j-33&&++b[r]>m:++r;for(j=r;m+1;putchar(j--?m<b[j]?79:32:(j=r,m--,10)));}

0

Rakieta: 130

(let l((a'()))(let((b(sort(string->list(read-line))char<?)))(if
(null? b)(apply map(λ x(map display x)(newline))a)(l(cons b a)))))

Wymaga padania spacjami, aby linie były równe długości.


0

C # - 209 174 bajtów

Racja, muszę spróbować golfa Code w pewnym momencie. Utworzono funkcję (r), która obraca tablicę i drukuje ją. Chyba trochę oszukuję, kiedy drukuję swoją tablicę znaków, ale jeśli nie możesz zrozumieć, dlaczego nie powinnaś być zła :)

Dzięki ProgramFOX za wskazówki :)

void r(string s){int x=s.IndexOf('\n'),j,i=-1,k,z=x+1;var y=new char[x*x+x];for(;++i<x;y[z*(i+1)-1]='\n')for(k=j=x;j>0;)if(s[i*z+--j]=='0')y[k--*z-i-2]='0';Console.Write(y);}

Oszukać

new char[x*x+x]wypełnia tablicę '\0'i nie' '


1
Usuwając nowe linie i usuwanie przestrzeń pomiędzy char[]i yzmniejszy liczbę znaków do 192 znaków. Ponadto, nie jest tak naprawdę konieczne podanie słowa kluczowego staticpodczas zamieszczania odpowiedzi tutaj. Usunięcie go zmniejszy liczbę twoich postaci do 185 znaków.
— ProgramFOX

Mogłem również usunąć „ref”, który został tam zapomniany od czasu wcześniejszej próby.
— WozzeC
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.