Rozpaczliwie szukam Świętego Mikołaja


13

Znajdź Świętego Mikołaja i jego renifery w zatłoczonej scenie.

Wejście

Dane wejściowe będą na STDIN i będą zmienną liczbą wierszy znaków o jednakowej, ale zmiennej długości. Jeśli Święty Mikołaj (reprezentowany przez postać S) jest na scenie, jego worek prezentów (reprezentowany przez postać P) będzie na jednej z sąsiadujących z nim pozycji (poziomo, pionowo lub po przekątnej). Jego renifery (każdy reprezentowany przez postać R) będą znajdować się wokół otaczającego go kwadratu 5x5. Jeśli Sna scenie pojawi się coś , co nie ma worka prezentów lub nie towarzyszy mu co najmniej 4 reniferów, to nie jest to Święty Mikołaj.

Wynik

Scena została oczyszczona z wszelkich zaciemnień (wszystkie postacie inne niż Święty Mikołaj, nie-prezenty, nierenifery zastąpione spacją), przedstawiające Świętego Mikołaja, jego worek prezentów i jego renifery - wszystkie inne postacie należy zastąpić spacjami. Jeśli Świętego Mikołaja i jego renifera nie ma na scenie, wyjmij go bez zmian. Gwarantujemy, że będzie tylko jedno rozwiązanie, więc nigdy nie będzie więcej niż jednego ważnego Świętego Mikołaja i nigdy nie będzie nosił więcej niż jednego worka prezentów.

Przykłady

W tych przykładach Ja tylko używając *charakter sprawiają, że łatwo zobaczyć S, Pi Rznaki, ale program powinien być w stanie obsłużyć każdy znak ASCII od !do `(33 do 96). Pominąłem małe litery i powyżej, aby uniknąć nieporozumień.

Wejście:

***********
***********
***********
*****R*****
******P****
*****S*****
*****R*****
****R**R***
***********
***********
***********
***********

Dane wyjściowe: (ignoruj ​​kropki, aby zmusić stronę do wyświetlania pustych linii)

.           
.          
.           
     R     
      P    
     S     
     R     
    R  R   
.           
.           
.           
.           

Wkład: (za mało reniferów)

***********
***********
***********
***********
******P****
*****S*****
*****R*****
****R**R***
***********
***********
***********
***********

Wynik:

***********
***********
***********
***********
******P****
*****S*****
*****R*****
****R**R***
***********
***********
***********
***********

Wejście: (bez worka prezentów)

***********
***********
***********
*****R*****
***********
*****S*****
*****R*****
****R**R***
***********
***********
***********
***********

Wynik:

***********
***********
***********
*****R*****
***********
*****S*****
*****R*****
****R**R***
***********
***********
***********
***********

Dane wejściowe: (prezenty nie są wystarczająco blisko)

***********
***********
***********
*****R*****
***********
*****S*P***
*****R*****
****R**R***
***********
***********
***********
***********

Wynik:

***********
***********
***********
*****R*****
***********
*****S*P***
*****R*****
****R**R***
***********
***********
***********
***********

Wejście: (jeden z reniferów poza polem 5x5 wokół Świętego Mikołaja)

***********
***********
***********
*****R*****
******P****
*****S*****
*****R*****
****R******
*******R***
***********
***********
***********

Wynik:

***********
***********
***********
*****R*****
******P****
*****S*****
*****R*****
****R******
*******R***
***********
***********
***********

Skrypty testowe

Podobnie jak w niektórych moich poprzednich pytaniach, po raz kolejny opracowałem skrypty testowe pierwotnie stworzone przez Joeya i Ventero, aby zapewnić kilka przypadków testowych dla tego pytania:

Stosowanie: ./test [your program and its arguments]

Wersja testu z tekstem jawnym : tekst zwykły

Nagrody

Każdy wpis, który mogę zweryfikować, który spełnia specyfikację, przechodzi testy i oczywiście miał pewne próby gry w golfa, otrzyma ode mnie opinię (więc proszę o podanie instrukcji użytkowania wraz z odpowiedzią). Najkrótsze rozwiązanie do końca 31.12.2013 zostanie zaakceptowane jako zwycięzca.


Zdaję sobie sprawę, że jest to podobne do mojego poprzedniego pytania Rozpoznawanie twarzy , ale od tego czasu minęło kilka lat. Przepraszam również za pominięcie piaskownicy pytań, ale ponieważ była związana z Bożym Narodzeniem, musiała zostać szybko opublikowana, w przeciwnym razie nie będzie to istotne.
— Gareth,

Pierwszy przykładowy wynik nie wyświetla się poprawnie (wydaje się być mniejszy).
— Dennis Jaheruddin

@DennisJaheruddin Wygląda na to, że Markdown usuwa wszystkie puste linie. Dodałem kropki na początku tych linii, aby pokazać, że tam są. Przepraszam za zamieszanie.
— Gareth

Odpowiedzi:


2

MATLAB: 110 , 95 znaków

f=@(x,y) filter2(ones(x),y);a=M==83;b=M==82;c=M==80;d=f(5,a&f(5,b)>3&f(3,c))&(a|b|c);if ~d,M,else,M(~d)=32,end

Nie jestem pewien, w jaki sposób dane wejściowe powinny być przetwarzane, ale reszta jest dość prosta.

Wersja normalnie sformatowana:

f=@(x,y) filter2(ones(x),y);
a=M==83;
b=M==82;
c=M==80;
d=f(5,a&f(5,b)>3&f(3,c))&(a|b|c);
if ~d
  M
else
  M(~d)=32
end

Przykładowe dane wejściowe:

M=['***********'
'***********'
'***********'
'*****R*****'
'******P****'
'*****SQL_2*'
'*****R*****'
'****R**R***'
'***********'
'***********'
'***********'
'***********'];

Hmmm, uruchamianie skryptów testowych na tym będzie niezręczne. Szybkie spojrzenie na kod sugeruje, że używasz tylko Przytoczone przykłady, które używają *znaków jak tłum, aby łatwiej było zobaczyć S, Pa Rznaki - Zważywszy, że badania w zakresie wykorzystania skryptu testu wszystkie znaki ASCII od 33 ( !) w górę do (włącznie) 96 (`` `). Wyjaśnię to w pytaniu. Zrobiłem tekstową wersję testów, które musisz zaliczyć, którą również dodam do pytania.
— Gareth,

@Gareth Zaktualizowano, wydaje się teraz zdawać testy. Szkoda, że ​​Święty Mikołaj nie nosi Quilt, uratowałby mi co najmniej 2 postacie.
— Dennis Jaheruddin,

W porządku. Nie mam Matlaba, więc właśnie pobieram Octave (który według mnie jest najlepszym darmowym sposobem na uruchomienie kodu Matlaba) i rano przejdę testy, żeby to sprawdzić.
— Gareth,

Ok, sprawdziłem to i wydaje się, że jest zgodne ze specyfikacją. Jedynym miejscem, w którym ma niesprawiedliwą przewagę, są wymagania dotyczące nakładów. Poparłem głosowanie, ale nie będę w stanie zaakceptować go jako zwycięzcy, dopóki nie odczyta danych wejściowych (z pliku, ponieważ wydaje się, że Matlab nie czyta ze STDIN).
— Gareth,

SQL_2
— Wsunąłeś

1

Python 2 ( 353 381)

import re,sys
a=sys.stdin.readlines()
h=len(a)
w=len(a[0])
a=''.join(a)+' '*99
print a
b=[''.join(q) for x in range(0,w) for y in range(0,h) for q in [[a[(y+z)*w+x:(y+z)*w+x+5] for z in range(0,5)]]]
for c in b:
 if c[12]=='S' and 'P' in ''.join([c[1+5*z:4+5*z] for z in range(1,4)]) and c.count('R')>3:
  a=re.sub('[^RPS]','.',c)
  w=h=5
for y in range(0,h):
 print a[y*w:(y+1)*w]

Pierwsza próba napisania kodu tak kompaktowego, jak to możliwe. Python nie jest tak naprawdę językiem do tego, ponieważ wcięcia i znaki nowej linii są po prostu wymagane przez projekt. Głównie wybieram używanie tego języka, ze względu na sposób, w jaki możesz grać z listami i ciągami jako listami. Język z łatwą obsługą macierzy byłby idealny do tego zadania, ale niestety nie znam żadnego z nich.

Aby przetestować, coś należy przypisać np

a=['1**********','*2*********','**3********','***4*******','****5*P****','*****S*****','*****,*****','****R**R***','***********','***********','****R******','**RPSRRR***']

Główną interesującą rzeczą w tym kodzie jest prawdopodobnie:

b=[''.join(q) for x in range(0,w) for y in range(0,h) for q in [[a[(y+z)*w+x:(y+z)*w+x+5] for z in range(0,5)]]]

co jest fantazyjnym sposobem pisania: „b staje się listą reprezentacji (ciąg 25 znaków) każdego kwadratu 5x5 w oryginalnej reprezentacji”.


Podczas gdy Matlab może mieć trudności z czytaniem ze STDIN, Python nie boję się. Odczytywanie danych wejściowych ze STDIN jest jednym z wymagań (aby umożliwić uruchomienie skryptu testowego tak, aby powstrzymać ludzi przed wymyśleniem własnego formatu wejściowego).
— Gareth,

Ups, całkowicie tego przegapiłem.
— Sumurai8,

Zmieniono kod, ale nie można przetestować, czy rzeczywiście tutaj działa. Powinien przeczytać w tym samym formacie, w jakim był.
— Sumurai8,

OK, miałem okazję teraz przetestować to i jest kilka problemów. 1) W przypadkach, w których znaleziono Świętego Mikołaja, dane wejściowe są wyprowadzane tak, jak przed rozwiązaniem. 2) Twoje rozwiązanie ma inny rozmiar niż wejście. W tym miejscu starałem się wyjaśnić pytanie - wszystkie postacie inne niż (santa, prezenty, renifery) powinny być zastąpione spacjami. Tak było w pierwszym przykładzie, ale nie zostało to wyraźnie określone w pytaniu. 3) Gdy Mikołaj nie zostanie znaleziony, wyjście ma podwójne odstępy między wierszami.
— Gareth,

0

W pliku powinien znajdować się tylko jeden Święty Mikołaj (jeśli więcej niż 2 „S”, potrzebuję zaktualizować kod).

Korzystanie z awk

cat santa.awk

BEGIN{FS=""}
{ for (i=1;i<=NF;i++)
         { a[NR FS i]=$i
           if ($i=="S") {l=NR;c=i}
         }
     }
END{ if (l=="") {print "No Santa";exit}
     for (i=l-1;i<=l+1;i++)
        for (j=c-1;j<=c+1;j++)
          if (a[i FS j]=="P") p++
     if (p<1) {print "Santa has no presents";exit}
     for (i=l-2;i<=l+2;i++)
        for (j=c-2;j<=c+2;j++)
          if (a[i FS j]=="R") r++
     if (r<4) {print "Santa has no enough reindeers";exit}
     else {  print "found Santa "
             for (i=1;i<=NR;i++)
               { for (j=1;j<=NF;j++)
                   if (a[i FS j]~/[R|S|P]/) {printf a[i FS j]} else {printf " "}
                 printf RS
                }
           }
    }

Uruchom komendę awk jak poniżej

awk -f santa.awk file

Wynik

found Santa



     R
    R R
    PS
    RR
    R  R

Przepraszamy za wcześniejsze sprawdzenie tego (jestem na wakacjach i nie mam łatwego dostępu do Wi-Fi). Niestety, 2 Ssą dozwolone, o ile tylko jeden jest „ważnym” Mikołajem. Testy (podane w pytaniu) mają kilka przypadków, które z tego powodu zakończyłyby się niepowodzeniem.
— Gareth
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.