Rzuć dywan

15

To pytanie jest inspirowane pytaniem Kevina Cruijssena .

Teraz, gdy dywan jest ułożony, chcemy go zwinąć. Twoim zadaniem jest napisanie programu, który pobiera ciąg znaków i zwraca spiralę wykonaną z tego ciągu (reprezentującą zwinięty dywan widziany z boku).

Procedura dla jednego kroku zwijania dywanu jest następująca. Jest przykład ilustrujący to, co mam na myśli. Zauważ, że przykład zaczyna się od częściowo zwiniętego dywanu dla lepszego zrozumienia:

ac
rpet
  • oddzielić „głowę” od „ogona” dywanu: głowa jest tym, co do tej pory zostało zwinięte, ogon jest tym, co pozostało do zrolowania.
Head: ac   Tail:
      rp          et
  • Obróć głowicę o 90 °, zgodnie z ruchem wskazówek zegara.
Rotated head: ra   Tail (unchanged):
              pc                       et
  • jeśli szerokość nowej głowy (tutaj 2) jest mniejsza lub równa długości ogona (tutaj 2)
    • następnie połóż go na ogonie
    • w przeciwnym razie dywan (jak na początku kroku) został zwinięty
New carpet: ra
            pc
            et

Powtórz procedurę tyle razy, ile potrzeba.


Dwa przykłady pokazujące wszystkie etapy zwijania dywanu:

carpet

 c
 arpet

  ac
  rpet

    ra
    pc
    et
0123456789

 0
 123456789

  10
  23456789

    21
    30
    456789

      432
      501
      6789

Niektóre szczegóły:

  • Nie musisz pokazywać wszystkich pośrednich kroków, tylko zwinięty dywan (np. Jeśli znajdziesz nie iteracyjny sposób obliczenia wyniku, jest on idealny). Ponadto nie musisz drukować żadnych wiodących białych znaków, w powyższych przykładach pokazuję je tylko w celu wyrównania elementów.
  • Dane wejściowe to ciąg znaków, lista / tablica znaków
  • Dane wyjściowe są drukowane na standardowe wyjście lub do pliku.
  • Dane wejściowe są ładne: długość wynosi co najmniej 1 znak, a co najwyżej stała wystarczająco mała, aby nie powodowała problemów, ale nie możesz użyć tej stałej w swoim programie; treść ciągu to tylko ładne znaki ([a-zA-Z0-9]), kodowanie według twoich preferencji.
  • To jest , więc wygrywa najkrótsza odpowiedź w bajtach. Nie pozwól, aby języki kod-golfowe zniechęcały Cię do publikowania odpowiedzi w językach niekodujących golfa. Spróbuj znaleźć możliwie najkrótszą odpowiedź na „dowolny” język programowania.
  • Domyślne luki są zabronione.
  • Jeśli to możliwe, dodaj link z testem swojego kodu.
  • Dodaj również wyjaśnienie swojej odpowiedzi, jeśli uważasz, że jest potrzebna.
Bromind
źródło
3
Ściśle związany
Giuseppe,
2
Także ten: codegolf.stackexchange.com/questions/125966/… , ale żaden z nich nie obejmuje kontroli zakończenia.
Bromind
3
Sugerowany przypadek testowy: ProgrammingPuzzlesAndCodeGolf- potknęła mnie ostateczna długość ogona większa niż 1.
Sok
1
Myślę, że zamieniłeś tutaj słowa „głowa” i „ogon”: „jeśli szerokość nowej głowy [...] jest większa lub równa długości ogona [...]”.
Erik the Outgolfer
1
Odebrane ze względu na zbyt restrykcyjne reguły wejścia / wyjścia; Usunąłem swoją odpowiedź w języku Python 2, ponieważ nie można jej użyć printw lambda.
Chas Brown,

Odpowiedzi:

7

Węgiel drzewny , 15 bajtów

FS«F¬℅§KV⁰⟲⁶→Pι

Wypróbuj online! Link jest do pełnej wersji kodu. Wyjaśnienie:

FS«

Pętla nad dywanem.

F¬℅§KV⁰

Sprawdź, czy jest coś powyżej kursora.

⟲⁶

Jeśli nie, zwinąć dywan.

→Pι

Przejdź w prawo i wypisz bieżący znak.

Przykład: Dla danych wejściowych 0123456789występują następujące działania:

0

0 jest drukowane.

01

Kursor przesuwa się w prawo i 1jest drukowany.

0
1

Ponieważ nic nie znajduje się powyżej 1, płótno jest obracane.

0
12

Kursor przesunie się w prawo i 2zostanie wydrukowany.

10
2

Ponieważ nic nie znajduje się powyżej 2, płótno jest obracane.

10
23

Kursor przesunie się w prawo i 3zostanie wydrukowany.

10
234

Kursor przesunie się w prawo i 4zostanie wydrukowany.

21
30
4

Ponieważ nic nie znajduje się powyżej 4, płótno jest obracane.

21
30
45

Kursor przesunie się w prawo i 5zostanie wydrukowany.

21
30
456

Kursor przesunie się w prawo i 6zostanie wydrukowany.

432
501
6

Ponieważ nic nie znajduje się powyżej 6, płótno jest obracane.

432
501
67

Kursor przesunie się w prawo i 7zostanie wydrukowany.

432
501
678

Kursor przesunie się w prawo i 8zostanie wydrukowany.

432
501
6789

Kursor przesunie się w prawo i 9zostanie wydrukowany.

Neil
źródło
To cudownie. Więc w zasadzie Charcoal ma wbudowanego operatora „roll” ?
Jonasz
1
@Jonah Cóż, nie będzie dla mnie toczyć się w miarę upływu czasu, ale wysyłając ciąg znaków po znaku, mogę toczyć się, jak idę, tak.
Neil,
3

Pyth, 37 bajtów

.U+j;bZ.WgleHJlhH,+_MChZ<eZJ>eZJ,]hQt

Spróbuj go online tutaj , lub sprawdzić wszystkie przypadki testowe od razu tutaj .

.U+j;bZ.WgleHJlhH,+_MChZ<eZJ>eZJ,]hQtQ   Implicit: Q=eval(input())
                                         Trailing Q inferred
                                 ]hQ     First character of Q, wrapped in an array
                                    tQ   All but the first character of Q
                                ,        2-element array of the two previous results
                                           This yields array with rolled carpet (as array of strings) followed by the tail
       .W                                While condition function is truthy, execute inner function, with initial value of the above:
         gleHJlhH                          Condition function, input H
             JlhH                            Number of layers in the current rolled carpet, store in J
          leH                                Lenth of the tail
         g   J                               Is the above greater than or equal to J?
                 ,+_MChZ<eZJ>eZJ           Inner function, input Z
                   _MChZ                     Rotate the current rolled carpet (transpose, then reverse each row)
                  +     <eZJ                 Append the first J characters of the tail as a new row
                 ,                           Pair the above with...
                            >eZJ             ... all but the first J characters of the tail - this is the new tail
.U+j;bZ                                  Join the carpet roll on newlines and append the tail, implicit print
Sok
źródło
3

Łuska , 24 bajty

►S=ÖLmFȯ:T↔ø§z:oΘḣĠ+CṘ2N

Wypróbuj online!

Wyjaśnienie

Implicit input, say s="carpets"

CṘ2N  Break s into chunks:
   N   Natural numbers: [1,2,3,4,..
 Ṙ2    Repeat each twice: [1,1,2,2,3,3,4,4,..
C      Break s into chunks of these lengths: ["c","a","rp","et","s"]
       The last chunk is shorter if we run out of characters.

§z:oΘḣĠ+  Attempt to merge suffix of chunks:
      Ġ    Cumulative reduce chunk list from right
       +   by concatenation: ["carpets","arpets","rpets","ets","s"]
   oΘḣ     Prefixes of chunk list (empty and nonempty): [[],["c"],..,["c","a","rp","et","s"]]
§z         Zip these by
  :        appending: [["carpets"],["c","arpets"],..,["c","a","rp","et","s"]]
           These are all versions of the chunk list where some suffix has been merged.

mFȯ:T↔ø  Roll each list:
m         Map
 F        reduce from left
      ø   starting from empty character matrix
  ȯ:T↔    by this function:
    T↔     Reverse and transpose (rotating by 90 degrees)
  ȯ:       then append next chunk as new row.
         Result: [["carpets"],["c","arpets"],..,["epr","tca","s"]]

►S=ÖL  Select the matrix rolled by the correct amount:
►       Find element that maximizes
 S=     being equal to
   ÖL   sort by length.
        This selects a matrix whose rows have non-decreasing lengths.
        Ties are broken by choosing the rightmost one.
       Result: ["ra","pc","ets"]

Implicitly print each row separated by newlines.
Zgarb
źródło
2

J , 69 bajtów

-3 bajty dzięki FrownyFrog

[:(}:@[,{:@[,])&>/[:((|:@|.@[,#@[$]);#@[}.])&>/^:(<:&#&>/)^:_,.@{.;}.

Wypróbuj online!

wyjaśnienie

[: (}:@[ , {:@[ , ])&>/ [: ((|:@|.@[ , #@[ {. ]) ; #@[ }. ])&>/^:(<:&#&>/)^:_ }. ;~ 1 1 $ {.

Algorytm jest prosty, mimo że jest nieco gadatliwy dla J.

Ogólna strategia: Zmniejsz wkład do kwadratowego stołu, z resztą (być może pustą).

Kiedy zmniejszamy, będziemy używać 2-elementowej listy pudeł. Nasz „dotychczasowy wynik” będzie pierwszym polem, a „produkty do przetworzenia” drugim polem. Pierwsze okno zostanie zainicjowane na początku wejścia (ale przekonwertowane na tabelę):

1 1 $ {.

a „elementy pozostałe do przetworzenia” będą ogonem wejściowym:

}. ;~

Teraz mamy:

┌─┬─────┐
│c│arpet│
└─┴─────┘

gdzie „c” jest w rzeczywistości tabelą 1x1.

Zmniejszamy to przy użyciu pętli J Do ... While:

^:(...)^:_

Gdzie część w nawiasie to warunek „kontynuuj”:

<:&#&>/

który mówi „kontynuuj, dopóki długość prawego pudełka jest większa lub równa długości lewego pudełka (tj. długość boku kwadratowej matrycy)

Co oznacza „kontynuuj”? Jest to zdefiniowane w czasowniku po lewej stronie pierwszego ^:, który mówi nam, jak wziąć bieżący wynik i wykonać następną iterację. Ten czasownik to:

((|:@|.@[ , #@[ {. ]) ; #@[ }. ])&>/

Rozbijmy to:

((|:@|.@[ , #@[ {. ]) ; #@[ }. ])&>/
(  verb in parens               )&>/ NB. put the verb in parens
                                     NB. between the two items
                                     NB. of our list, and unbox
                                     NB. them into left / right
                                     NB. args ([ / ]) for the verb
 (|:@|.@[ , #@[ {. ]) ; #@[ }. ]     NB. breaking down verb in 
                                     NB. parens...
                      ; ....         NB. new "remaining items":
                            }. ]     NB. remove from remaining
                        #@[          NB. the size of a side of
                                     NB. the result matrix
                ....  ;              NB. new "result":
  |:@|.@[                            NB. rotate existing result
          ,                          NB. and put it on top of
            #@[ {. ]                 NB. the items we removed
                                     NB. from remaining items

Oznacza to, że jest to tylko algorytm opisany w OP przetłumaczony dosłownie na J.

Na koniec zajmujemy się (ewentualnie 0) resztkami, ogonem naszej rolki dywanowej:

(}:@[ , {:@[ , ])&>/

To mówi „weź wszystko oprócz ostatniego wiązu wyniku”:

}:@[ 

i dołącz go do ,ostatnich elementów wyniku, {:@[a pozostałe elementy dołączone do tego ostatniego elementu, ]

Jonasz
źródło
Ach, J ... litery są dla noobów
RK.
,.może robić to, co 1 1$]robi i $może być używane jako {..
FrownyFrog,
@FrownyFrog ty. Dostałem go do 70 bajtów z twoją pierwszą sugestią, ale nie byłem pewien, czy zrozumiałem $ can be used as {.- czy możesz to wyjaśnić?
Jonasz
1
W ostatnim wierszu objaśnienia używasz {. obciąć, że o ile rozumiem, można być $.
FrownyFrog,
Ponadto można wymienić prawy [: z @
FrownyFrog
1

R , 146 132 bajtów

function(s){m=F[F]
while({m=rbind(t(m)[,F:0],s[1:F])
s=s[-1:-F]
length(s)>sum(F<-dim(m))})0
write(m[F:1,],1,F[1],,"")
cat(s,sep="")}

Wypróbuj online!

Realizuje procedurę zwijania dywanu. Pobiera dane wejściowe jako listę znaków i drukuje na standardowe wyjście.

Zaoszczędzono 14 bajtów, znajdując sposób użycia do-whilepętli i inicjując za pomocą F.

function(s){
m=F[F]					# logical(0); create an empty array (this gets automatically promoted to character(0) later
while(					# do-while loop
      {m=rbind(t(m)[,F:0],s[1:F])	# rotate m counterclockwise and add the first F characters of s to the bottom
       s=s[-1:-F]			# remove those characters
       length(s)>sum(F<-dim(m))})0	# while the number of characters remaining is greater than the sum of m's dimensions
write(m[F:1,],1,F[1],,"")		# write the rolled portion write writes down the columns, we reverse each column
cat(s,sep="")				# and write the remaining characters
}
Giuseppe
źródło
1

Galaretka , 30 bajtów

Wydaje się zbyt długo ...

ḢW,ðZU;Ls@¥©ḢWɗ,®Ẏ¤ð/ẈṢƑ$¿ḢY;Ɗ

Wypróbuj online!

W jaki sposób?

ḢW,ðZU;Ls@¥©ḢWɗ,®Ẏ¤ð/ẈṢƑ$¿ḢY;Ɗ - Main Link: list of characters
Ḣ                              - pop and yield head
 W                             - wrap in a list
  ,                            - pair with (the remaining list after Ḣ)
                         ¿     - while...
                        $      - ...condition: last two links as a monad:
                     Ẉ         -   length of each
                       Ƒ       -   is invariant under:
                      Ṣ        -     sort
                    /          - ...do: reduce by:
   ð               ð           -   the enclosed dyadic chain -- i.e. f(head, tail):
    Z                          -     transpose
     U                         -     reverse each (giving a rotated head)
              ɗ                -     last three links as a dyad:
          ¥                    -       last two links as a dyad:
       L                       -         length (i.e. number of rows in current roll)
         @                     -         with swapped arguments:
        s                      -           split (the tail) into chunks of that length
           ©                   -       (copy to register for later)
            Ḣ                  -       pop and yield head (Note register "copy" is altered too)
             W                 -       wrap in a list
      ;                        -     concatenate (the rotated head with the first chunk of the tail)
                  ¤            -     nilad followed by link(s) as a nilad:
                ®              -       recall from register (other chunks of tail, or an empty list)
                 Ẏ             -       tighten (the chunks to a flat list)
               ,               -     pair (the concatenate result with the tightened chunks)
                             Ɗ - last three links as a monad:
                          Ḣ    -   pop and yield head
                           Y   -   join with newline characters
                            ;  -   concatenate (the remaining tail)
                               - when running as a full program implicitly prints
Jonathan Allan
źródło
1

05AB1E , 41 bajtów

g©L¦€DD2šηO®>‹Ï©IŽ8OS®g4α._.ΛðÜI®O®g->.$«

O wiele za długo, ale chciałem użyć Canvas. Co było prawdopodobnie złym wyborem, kiedy go skończyłem i okazało się, że było tak długo ..

Wypróbuj online . (Brak zestawu testów, ponieważ wydaje się, że jest dziwny problem z wbudowanym ..)

Wyjaśnienie:

Zacznę od ogólnego wyjaśnienia obszaru roboczego i tego, co chciałem, aby mój kod miał osiągnąć. Bardziej szczegółowe informacje można znaleźć w tym moim odpowiednim poradniku 05AB1E , ale do tego wyzwania chciałem wykonać następujące czynności:

Wbudowane płótno ma trzy parametry:

  • za[2,2,3,3,4,4,5,5,...]
  • b
  • do[2),0,6,4][,,,]ncarpet[0,6,4,2)]0123456789ABCDEFGHI[6,4,2),0]

Co do kodu:

g                # Get the length of the (implicit) input-string
 ©               # Store it in the register (without popping)
  L              # Create a list in the range [1,length]
   ¦             # Remove the first item to make the range [2,length]
    D           # Duplicate each to get the list [2,2,3,3,4,4,5,5,...]
      D2š        # Create a copy and prepend a 2: [2,2,2,3,3,4,4,5,5,...]
         η       # Get the prefixes: [[2],[2,2],[2,2,2],[2,2,2,3],...]
          O      # Sum each prefix: [2,4,6,9,12,16,20,...]
           ®     # Push the length from the register again
            >‹   # Check for each summed prefix if it's <= length
              Ï  # And only leave the truthy values
               © # And store this in the register (without popping)
                 # (This is our `a` for the Canvas builtin)
I                # Push the input-string
                 # (This is our `b` for the Canvas builtin)
Ž8O              # Push compressed integer 2064
   S             # Converted to a list of digits: [2,0,6,4]
    ®g           # Push the list from the register, and get its length
      4α         # Get the absolute difference with 4
        ._       # And rotate the [2,0,6,4] that many times towards the left
                 # (This is our `c` for the Canvas builtin)
               # Now use the Canvas builtin, without printing it yet
  ðÜ             # Remove any trailing spaces (since the Canvas implicitly makes a rectangle)
     ®O          # Push the sum of the list from the register
       ®g-       # Subtract the length of the list from the register
          >      # And add 1
    I      .$    # Remove that many leading characters from the input-string
             «   # And append it at the end of the roll created by the Canvas
                 # (after which the result is output implicitly)

Zobacz moją wskazówkę 05AB1E (rozdział Jak skompresować duże liczby całkowite? ), Aby zrozumieć, dlaczego tak Ž8Ojest 2064.

Kevin Cruijssen
źródło
0

Python 3 , 112 bajtów

r=lambda t,h=[[]]:len(h)>len(t)and h[:-1]+[h[-1]+list(t)]or r(t[len(h):],list(zip(*h[::-1]))+[list(t)[:len(h)]])

W tym przypadku wynikiem jest wartość funkcji.

Wypróbuj online!

Jeśli wolisz, oto inne (dłuższe, 129 bajtów ) rozwiązanie, które drukuje bezpośrednio zrolowane dane wejściowe:

r=lambda t,h=['']:len(h)>len(t)and set(map(print,h[:-1]+[h[-1]+t]))or r(t[len(h):],list(map(''.join,zip(*h[::-1])))+[t[:len(h)]])

Wypróbuj online!

PieCot
źródło
1
trzeba go wydrukować
tylko ASCII
@ Tylko ASCII: Cytując autora pytania: „Jeśli powrót zamiast drukowania pokazuje wielką poprawę lub fajną sztuczkę, opublikuj odpowiedź (i wyraźnie, że wracasz, a nie drukujesz)” . Więc myślę, że jest w porządku.
PieCot
0

MATLAB / oktawa , 154 bajtów

Nie najkrótsza, ale gra w golfa w MATLAB / Octave jest zawsze fajna :)

function h=r(t,h);n=fliplr(h');s=size(n,2);q=numel(t);if s<=q h=r(t(max(s,1)+1:end),[n; t(1:max(s,1))]);elseif q>0 h(:,end+q)=' ';h(end,end-q+1:end)=t;end

Wypróbuj online!

PieCot
źródło
1
niestety, op mówi, że musisz wydrukować
tylko ASCII
@ Tylko ASCII, jak wyjaśniono tutaj ( it.mathworks.com/matlabcentral/answers/… ), standardowe wyjście w świecie Matlaba odnosi się do okna poleceń. Biorąc pod uwagę, że wynik oceny każdego polecenia jest automatycznie drukowany w oknie poleceń, myślę, że tę odpowiedź można uznać za zgodną z wymogami pytania.
PieCot
Może chce zrobić, że jaśniejsze następnie
ASCII tylko
@ Tylko ASCII Naprawdę nie rozumiem, co masz na myśli. Jest to funkcja, którą nazywacie, wynik zostanie automatycznie wydrukowany w oknie poleceń (tj. Standardowe wyjście). Co jest z tym nie tak? Nawet odpowiedź R działa w ten sposób ...
PieCot 14.04.19
1
W tej chwili dispto, powiedziałbym, należy usunąć disp, aby pozwolić ludziom, że nie wiedzą, że R nie pisać do STDOUT domyślnie
ASCII tylko