Rozwiń tablicę C.


36

W języku programowania C tablice są zdefiniowane w następujący sposób:

int foo[] = {4, 8, 15, 16, 23, 42};      //Foo implicitly has a size of 6

Rozmiar tablicy wynika z elementów inicjujących, które w tym przypadku wynoszą 6. Możesz również napisać tablicę C w ten sposób, jawnie zmieniając jej rozmiar, a następnie definiując każdy element w kolejności:

int foo[6];        //Give the array an explicit size of 6
foo[0] = 4;
foo[1] = 8;
foo[2] = 15;
foo[3] = 16;
foo[4] = 23;
foo[5] = 42;

Wyzwanie

Musisz napisać program lub funkcję, która rozwija tablice od pierwszej do drugiej. Ponieważ piszesz program, aby wydłużyć kod i kochasz ironię, musisz go skrócić tak krótko, jak to możliwe.

Dane wejściowe będą ciągiem znaków reprezentującym oryginalną tablicę, a dane wyjściowe będą rozszerzoną definicją tablicy. Możesz bezpiecznie założyć, że dane wejściowe zawsze będą wyglądać następująco:

<type> <array_name>[] = {<int>, <int>, <int> ... };

„Type” i „array_name” składają się wyłącznie ze znaków alfabetu i znaków podkreślenia _. Elementami listy zawsze będzie liczba z zakresu od -2 147 483 648 do 2 147 483 647. Wejścia w dowolnym innym formacie nie muszą być obsługiwane.

Biała spacja na wyjściu musi dokładnie pasować do białej spacji na wyjściu testowym, chociaż dozwolony jest końcowy znak nowej linii.

Test IO:

#in
short array[] = {4, 3, 2, 1};

#out
short array[4];
array[0] = 4;
array[1] = 3;
array[2] = 2;
array[3] = 1;


#in
spam EGGS[] = {42};

#out
spam EGGS[1];
EGGS[0] = 42;


#in
terrible_long_type_name awful_array_name[] = {7, -8, 1337, 0, 13};

#out
terrible_long_type_name awful_array_name[5];
awful_array_name[0] = 7;
awful_array_name[1] = -8;
awful_array_name[2] = 1337;
awful_array_name[3] = 0;
awful_array_name[4] = 13;

Zgłoszenia w dowolnym języku są zachęcane, ale punkty bonusowe, jeśli możesz to zrobić w C.

Tabela liderów:

Oto tabela liderów przedstawiająca najlepsze odpowiedzi:


2
Czy spacje między indeksem tablicy, znakiem równości i wartościami wymaganymi w danych wyjściowych? Na przykład, czy foo[0]=1;byłby do przyjęcia?
— Mego

@Mego To byłoby nie do przyjęcia. Biała spacja jest wymagana. Zmienię to.
— DJMcMayhem

Końcowa nowa linia jest dozwolona?
— Luis Mendo

Czy funkcje są dozwolone?
— Mego

Czy można zwracać dane wyjściowe zamiast je drukować? (w przypadku funkcji)
— vaultah 15.04.16

Odpowiedzi:


12

Pyth, 44 bajty

++Khcz\]lJ:z"-?\d+"1"];"VJs[ecKd~hZ"] = "N\;

Zestaw testowy

Wyrażenie regularne i odcinanie łańcucha. Niezbyt sprytnie.

Wyjaśnienie:

++Khcz\]lJ:z"-?\d+"1"];"VJs[ecKd~hZ"] = "N\;
                                                Implicit: z = input()
    cz\]                                        Chop z on ']'
   h                                            Take string before the ']'
  K                                             Store it in K
 +                                              Add to that
         :z"-?\d+"1                             Find all numbers in the input
        J                                       Store them in J
       l                                        Take its length.
+                  "];"                         Add on "];" and print.
                       VJ                       For N in J:
                         s[                     Print the following, concatenated:
                            cKd                 Chop K on spaces.
                           e                    Take the last piece (array name)
                               ~hZ              The current interation number
                                  "] = "        That string
                                        N       The number from the input
                                         \;     And the trailing semicolon.

Ta odpowiedź jest moim cierniem. Myślałem, że uda mi się wygrać w vimie, ale przez całe moje życie nie mogę oderwać ostatnich 2-3 bajtów. = D Ładna odpowiedź!
— DJMcMayhem

28

Vim, 54, 52, 49 47 klawiszy


2wa0<esc>qqYp<c-a>6ldf @qq@q$dT]dd:%norm dwf{xwC;<CR>gg"0P

Wyjaśnienie:

2wa0<esc>                     'Move 2 words forward, and insert a 0.
         qq                   'Start recording in register Q
           Yp                 'Duplicate the line
             <c-a>6l          'Increment the next number then move 6 spaces right
                    df        'Delete until the next space
                       @qq@q  'Recursively call this macro

Teraz nasz bufor wygląda następująco:

int foo[0] = {4, 8, 15, 16, 23, 42};
int foo[1] = {8, 15, 16, 23, 42};
int foo[2] = {15, 16, 23, 42};
int foo[3] = {16, 23, 42};
int foo[4] = {23, 42};
int foo[5] = {42};
int foo[6] = {42};

a nasz kursor znajduje się w ostatniej linii.

Druga połowa:

$                           'Move to the end of the line
 dT]                        'Delete back until we hit a ']'
    dd                      'Delete this whole line.
      :%norm         <CR>   'Apply the following keystrokes to every line:
             dw             'Delete a word (in this case "int")
               f{x          '(f)ind the next '{', then delete it.
                  wC;       'Move a word, then (C)hange to the end of this line, 
                            'and enter a ';'

Teraz wszystko wygląda dobrze, wystarczy dodać oryginalną deklarację tablicową. Więc robimy:

gg        'Move to line one
  "0P     'Print buffer '0' behind us. Buffer '0' always holds the last deleted line,
          'Which in this case is "int foo[6];"

3
Ilekroć czytam vim-golfa, zdaję sobie sprawę, że całe kodowanie, które robię (głównie polecenia klawiaturowe w moich różnych edytorach GUI) wygląda podobnie do tego, a mój umysł trochę się ugina (Vim jest po prostu kompletny (i fajniejszy)) : P
— cat

Nie mogę tego uruchomić - kiedy piszę pierwsze „@q” (z „@ qq @ q”), makro działa wtedy i najwyraźniej działa dalej niż powinno, uzyskując rzeczy podobne int foo[6] = {i kończące się int foo[12(kursor na „2”)
— LordAro

@ LordAro Prawdopodobnie powinienem o tym wspomnieć. Dzieje się tak, ponieważ w q znajduje się już makro, które działa podczas nagrywania, co psuje go. Wyjaśniłem, jak to obejść tutaj: codegolf.stackexchange.com/a/74663/31716
— DJMcMayhem

1
@ LordAro O rany, wiem co to powoduje. Zmieniłem df<space>na, dWaby zapisać bajt, ale zapomniałem, że df<space>wyrwie się z makra w linii 6, ale dWnie robi tego. Cofam wersję. Dzięki za zwrócenie na to uwagi!
— DJMcMayhem

1
Chociaż nie jest to najkrótsza odpowiedź, jest zdecydowanie najbardziej imponująca.
— isaacg

10

Siatkówka, 108 104 100 69 bajtów

Liczba bajtów zakłada kodowanie ISO 8859-1.

].+{((\S+ ?)+)
$#2];$1
+`((\w+\[).+;(\S+ )*)(-?\d+).+
$1¶$2$#3] = $4;

Pokonaj to, PowerShell ...

Wyjaśnienie kodu

Pierwsza linia: ].+{((\S+ ?)+)

Po pierwsze, musimy zachować typ, nazwę tablicy i nawias otwierający (to oszczędza bajt), więc nie pasujemy do nich. Więc dopasować wspornik zamykający dowolną liczbę znaków, a otwór nawias klamrowy: ].+{. Następnie dopasowujemy listę numerów. Najkrótsza udało mi się znaleźć do tej pory to: ((\S+ ?)+). Pasuje do dowolnej liczby znaków niż kosmiczne (w tym numery możliwe znak ujemny i możliwe przecinek), a następnie za pomocą przestrzeni, które mogą lub nie mogą być tam: \S+ ?. Ta grupa znaków jest następnie powtarzana tyle razy, ile potrzeba: (\S+ ?)+i umieszczana w dużej grupie przechwytywania. Pamiętaj, że nie pasujemy do zamykającego nawiasu klamrowego ani średnika. Wyjaśnienie trzeciego wiersza mówi dlaczego.

Druga linia: $#2];$1

Ponieważ dopasowaliśmy tylko część danych wejściowych, niedopasowane części nadal tam będą. Więc umieścić długość listy po nawiasie otwierającym niedopasowanej: $#2. Modyfikator zastępowania #pomaga nam w tym, ponieważ daje nam liczbę dopasowań wykonanych przez konkretną grupę przechwytującą. W tym przypadku grupa przechwytująca2 . Następnie dodajemy nawias zamykający i średnik, a na koniec całą naszą listę.

Z wejściem short array[] = {4, 3, 2, 1}; wewnętrzna reprezentacja po tym zastąpieniu to:

krótka tablica [4]; 4, 3, 2, 1};

(zwróć uwagę na zamykający nawias klamrowy i średnik)

Trzecia linia: +`((\w+[).+;(\S+ )*)(-?\d+).+

To jest sekcja zapętlona. Oznacza to, że działa, dopóki żaden stopień w pętli nie zmieni danych wejściowych. Najpierw musimy dopasować nazwę tablicy, a następnie za pomocą uchwytu otwierającego: (\w+\[). Potem dowolną ilość dowolnych znaków i średnik: .+;. Następnie dopasować listę ponownie, ale tym razem tylko liczby i przecinek po każdym numerze, który ma miejsce po nich: (\S+ )*. Następnie uchwycić ostatni numer w liście: (-?\d+)i wszelkie pozostałe znaki za nim: .+.

Czwarta linia: $1¶$2$#3] = $4;

Następnie zastąp go nazwą tablicy i listy zakończoną nową linią: $1¶. Następnie kładziemy nazwę tablicy, a następnie długości poprzednio dopasowane listy, bez ostatniego elementu (zasadniczo list.length - 1) $2$#3. Po nim nawias zamykający i operator przypisania ze spacjami, a następnie ostatni element naszej listy liczb:] = $4;

Po pierwszej wymianie wewnętrzna reprezentacja wygląda następująco:

short array[4];4, 3, 2, 
array[3] = 1;

Zauważ, że zamykające się nawiasy klamrowe i średnik zniknęły dzięki .+końcowi trzeciej linii. Po trzech kolejnych zamianach wewnętrzna reprezentacja wygląda następująco:

short array[4];
array[0] = 4;
array[1] = 3;
array[2] = 2;
array[3] = 1;

Ponieważ nic nie pasuje do trzeciej linii, czwarta nic nie zastępuje, a łańcuch jest zwracany.

TL; DR: Najpierw nieco zmienimy format listy int. Następnie bierzemy ostatni element listy i nazwę i umieszczamy je po inicjalizacji tablicy. Robimy to, dopóki lista int nie będzie pusta. Następnie zwracamy zmieniony kod.

Wypróbuj online!


Ktoś mnie pobił .... :(
— CalculatorFeline

M!`i G`są podobne, ale nie do końca takie same. Bądź ostrożny.
— CalculatorFeline

Wyjaśnienie trzeciego wiersza mnie dezorientuje. Pierwszy przedmiot jest jedynym bez spacji, a nie ostatnim.
— CalculatorFeline

@CatsAreFluffy Właśnie próbowałem nieco zmienić brzmienie. Miałem na myśli spację po liczbie, a nie poprzedzającą ją. Chyba nie w pełni zrozumiałem znaczenie „za”. Naprawdę nie powinienem pisać objaśnień kodu o 2 w nocy.
— daavko

@daavko „Behind” zwykle oznacza „po”, czyli „po”, w potocznym języku angielskim. Było dobrze
— Pozew funduszu Moniki

9

V, 37 bajtów

2Eé0òYp6ldf ò$dT]ddÎdwf{xwC;
gg"1P

V to napisany przeze mnie napisany w 2D język golfowy oparty na łańcuchach. Działa to od zatwierdzenia 17 .

Wyjaśnienie:

Jest to prawie bezpośrednie tłumaczenie mojej odpowiedzi vima , choć znacznie krótsze.

2E                               "Move to the end of 2 words forward.
  é0                             "Insert a single '0'
    ò       ò                    "Recursively do:
     Yp6ldf                      "Yank, paste, move 6 right, delete until space.
             $dT]                "Move to the end of line, delete backwards until ']'
                 dd              "Delete this line
                   Î             "Apply the following to every line:
                    dwf{xwC;<\n> "Delete word, move to '{' and delete it, Change to end of line, and enter ';'

Mamy po prostu:

gg"1P     "Move to line 1, and paste buffer '1' behind us.

Ponieważ trudno jest wprowadzić to szaleństwo w trybie Unicode, możesz utworzyć plik za pomocą tego odwracalnego zrzutu heksadecymalnego:

00000000: 3245 e930 f259 7001 366c 6466 20f2 2464  2E.0.Yp.6ldf .$d
00000010: 545d 6464 ce64 7766 7b78 7743 3b0d 6767  T]dd.dwf{xwC;.gg
00000020: 2231 500a                                "1P.

Można to uruchomić, instalując V i wpisując:

python main.py c_array.v --f=file_with_original_text.txt

1
Designed off of vim.2 notatki: 1. większość ludzi mówi , że fromnie off of, i 2. dlaczego tak nie było. +1
— Rɪᴋᴇʀ

8

C, 215 bajtów , 196 bajtów

19 bajtów zapisanych dzięki @tucuxi!

Gra w golfa:

char i[99],o[999],b[99],z[99];t,x,n,c;main(){gets(i);sscanf(i,"%s %[^[]s",b,z);while(sscanf(i+t,"%*[^0-9]%d%n",&x,&n)==1)sprintf(o,"%s[%d] = %d;\n",z,c++,x),t+=n;printf("%s %s[%d];\n%s",b,z,c,o);}

Nie golfowany:

/*
 *  Global strings:
 *   i: input string
 *   o: output string
 *   b: input array type
 *   z: input array name
*/
char i[ 99 ], o[ 999 ], b[ 99 ], z[ 99 ];

/* Global ints initialized to zeros */
t, x, n, c;

main()
{
    /* Grab input string from stdin, store into i */
    gets( i );

    /* Grab the <type> <array_name> and store into b and z */
    sscanf( i, "%s %[^[]s", b, z );

    /* Grab only the int values and concatenate to output string */
    while( sscanf( i + t, "%*[^0-9]%d%n", &x, &n ) == 1 )
    {
        /* Format the string and store into a */
        sprintf( o, "%s[%d] = %d;\n", z, c++, x );

        /* Get the current location of the pointer */
        t += n;
    }

    /* Print the <type> <array_name>[<size>]; and output string */
    printf( "%s %s[%d];\n%s", b, z, c, o );
}

Połączyć:

http://ideone.com/h81XbI

Wyjaśnienie:

Aby uzyskać <type> <array_name>, sscanf()ciąg formatu jest następujący:

%s          A string delimited by a space
    %[^[]   The character set that contains anything but a `[` symbol
         s  A string of that character set

Aby wyodrębnić wartości int z ciągu int foo[] = {4, 8, 15, 16, 23, 42};, zasadniczo tokenizuję ciąg za pomocą tej funkcji:

while( sscanf( i + t, "%*[^0-9]%d%n", &x, &n ) == 1 )

gdzie:

  • ito ciąg wejściowy (a char*)
  • t to przesunięcie położenia wskaźnika na i
  • xto rzeczywista intparsowana z ciągu
  • n to łączna liczba zużytych znaków, w tym znaleziona cyfra

sscanf()Ciąg formatu oznacza to:

%*            Ignore the following, which is..
  [^0-9]      ..anything that isn't a digit
        %d    Read and store the digit found
          %n  Store the number of characters consumed

Jeśli wizualizujesz ciąg wejściowy jako tablicę znaków:

int foo[] = {4, 8, 15, 16, 23, 42};
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
00000000001111111111222222222233333
01234567890123456789012345678901234

z int 4byciem zlokalizowanym pod indeksem 13, 8pod indeksem 16 i tak dalej, tak wygląda wynik każdego uruchomienia w pętli:

Run 1)  String: "int foo[] = {4, 8, 15, 16, 23, 42};"
        Starting string pointer: str[ 0 ]
        Num chars consumed until after found digit: 14
        Digit that was found: 4
        Ending string pointer: str[ 14 ]

Run 2)  String: ", 8, 15, 16, 23, 42};"
        Starting string pointer: str[ 14 ]
        Num chars consumed until after found digit: 3
        Digit that was found: 8
        Ending string pointer: str[ 17 ]

Run 3)  String: ", 15, 16, 23, 42};"
        Starting string pointer: str[ 17 ]
        Num chars consumed until after found digit: 4
        Digit that was found: 15
        Ending string pointer: str[ 21 ]

Run 4)  String: ", 16, 23, 42};"
        Starting string pointer: str[ 21 ]
        Num chars consumed until after found digit: 4
        Digit that was found: 16
        Ending string pointer: str[ 25 ]

Run 5)  String: ", 23, 42};"
        Starting string pointer: str[ 25 ]
        Num chars consumed until after found digit: 4
        Digit that was found: 23
        Ending string pointer: str[ 29 ]

Run 6)  String: ", 42};"
        Starting string pointer: str[ 29 ]
        Num chars consumed until after found digit: 4
        Digit that was found: 42
        Ending string pointer: str[ 33 ]

1
możesz uniknąć używania strcat, łącząc owewnątrz sprintf, przez %s. Powinno to ogolić około 7 znaków.
— tucuxi 18.04.16

@tucuxi Ah, dobry chwyt. Dzięki!
— homersimpson 18.04.16

7

C, 195 180 bajtów

195-bajtowy oryginał:

grał w golfa:

char*a,*b,*c,*d;j;main(i){scanf("%ms %m[^]]%m[^;]",&a,&b,&c);
for(d=c;*d++;i+=*d==44);printf("%s %s%d];\n",a,b,i);
for(d=strtok(c,"] =,{}");j<i;j++,d=strtok(0," ,}"))printf("%s%d] = %s;\n",b,j,d);}

bez golfa:

char*a,*b,*c,*d;
j;
main(i){
    scanf("%ms %m[^]]%m[^;]",&a,&b,&c); // m-modifier does its own mallocs
    for(d=c;*d++;i+=*d==44);            // count commas
    printf("%s %s%d];\n",a,b,i);        // first line
    for(d=strtok(c,"] =,{}");j<i;j++,d=strtok(0," ,}"))
        printf("%s%d] = %s;\n",b,j,d);  // each array value
}

Oba skróty używają mmodyfikatora, aby uzyskać od skanów %sprzydział własnej pamięci (zapisuje deklarowanie tablic znaków) i używają strtok(która jest domyślnie dostępna, bez uwzględnienia) do wykonania analizy składni liczbowej.


Aktualizacja 180-bajtowa:

char*a,*b,*c,e[999];i;main(){scanf("%ms %m[^]]%m[^}]",&a,&b,&c);
for(c=strtok(c,"] =,{}");sprintf(e,"%s%s%d] = %s;\n",e,b,i++,c),
c=strtok(0," ,"););printf("%s %s%d];\n%s",a,b,i,e);}

bez golfa:

char*a,*b,*c,e[999];
i;
main(){
    scanf("%ms %m[^]]%m[^}]",&a,&b,&c);
    for(c=strtok(c,"] =,{}");sprintf(e,"%s%s%d] = %s;\n",e,b,i++,c),c=strtok(0," ,"););
    printf("%s %s%d];\n%s",a,b,i,e);
}

Wykorzystuje pomysł bnf679 dołączania do ciągu, aby uniknąć konieczności liczenia przecinków.


6

Python 3.6 (wersja wstępna), 133

m,p=str.split,print;y,u=m(input(),'[');t,n=m(y);i=m(u[5:-2],', ')
l=len(i);p(t,n+f'[{l}];')
for x in range(l):p(n+f'[{x}] = {i[x]};')

Często korzysta z struny typu F. .

Wersja bez golfa:

y, u = input().split('[')
t, n = y.split()
i = u[5:-2].split(', ')
l = len(i)
print(t, n + f'[{l}];')
for x in range(l):
    print(n + f'[{x}] = {i[x]};')

1
Woah, zapomniałem o f-stringach. Będą one bardzo przydatne do gry w golfa!
— Morgan Thrapp,

Myślę, że możesz zapisać bajt, używając rozumienia listy zamiast normalnej pętli
— someonewithpc

@someonewithpc: nope, faktycznie
— dodałby

5

Ruby, 127 110 108 99 88 bajtów

Funkcja anonimowa z jednym argumentem wejściowym.Pełny program odczytuje dane wejściowe ze STDIN. (Jeśli wpiszesz plik do potoku, końcowy znak nowej linii jest opcjonalny). Zwraca Drukuje ciąg wyjściowy.

@TimmyD chwalił się swoim rozwiązaniem pokonując wszystkie inne nie-esolangi jako wyzwanie, i wreszcie pokonał (w chwili pisania) 114 bajtowe rozwiązanie Powershell, które opublikowali. Sztuczka Cᴏɴᴏʀ O'Bʀɪᴇɴ z dzieleniem się] i drugiej połowy w celu uzyskania liczb.

Muszę więcej korzystać z operatora splat. To takie przydatne!

Wypożyczył sztuczkę z odpowiedzi JavaScript ES6 @ Neil, aby zaoszczędzić więcej bajtów, skanując w poszukiwaniu słów zamiast używać gsubi split...

t,n,*l=gets.scan /-?\w+/;i=-1
puts t+" #{n}[#{l.size}];",l.map{|e|n+"[#{i+=1}] = #{e};"}

AFAICT zadaniem jest napisanie pełnego programu.
— vaultah 15.04.16

@vaultah Domyślnym kodem do golfa jest program lub funkcja
— Mego

@Mego: OP powiedział „Musisz napisać program”
— vaultah

@vaultah normalnie powiedziałbym, że kod golf pozwala mi korzystać z funkcji, ale pełny program oszczędził mi 2 bajty, więc czemu nie?
— Wartość tuszu

Hej ... Nie sądzę, że PowerShell może do tego dojść. Zdobądź +1
— AdmBorkBork 18.04.16

4

05AB1E , 52 50 47 bajtów

Kod:

… = ¡`¦¨¨ð-',¡©gr¨s«„];«,®v¹ð¡¦¬s\¨N"] = "y';J,

Wykorzystuje kodowanie CP-1252 . Wypróbuj online! .


1
Doszło do tego, że pomijam wszystkie inne odpowiedzi, szukając tylko odpowiedzi 05AB1E. Język absolutnie mnie fascynuje.
— WorseDoughnut 18.04.16

1
@WorseDoughnut Dziękujemy! To najładniejsza rzecz, jaką ktoś mi powiedział o 05AB1E :)!
— Adnan

4

JavaScript (ES6), 100 bajtów

(s,[t,n,...m]=s.match(/-?\w+/g))=>t+` ${n}[${m.length}];`+m.map((v,i)=>`
${n}[${i}] = ${v};`).join``

Ponieważ tylko słowa są ważne, działa to po prostu dopasowując wszystkie słowa w oryginalnym ciągu, plus poprzedzające znaki minus, a następnie budując wynik. (Początkowo myślałem, że zamierzam użyć, replaceale okazało się, że to czerwony śledź.)


[t,n,...m]prawie mistyczna wizja
— edc65 16.04.16


4

Pip , 48 47 bajtów

qR`(\S+)(. = ).(.+)}`{[b#Yd^k']';.n.b.,#y.c.y]}

Pobiera dane wejściowe ze standardowego wejścia i drukuje na standardowe wyjście.

Wyjaśnienie

Tl; dr: Wykonuje zamianę wyrażenia regularnego, używając grup przechwytywania i funkcji zwrotnej do skonstruowania wyniku.

qSpecjalna zmienna czyta wiersz wejścia. Wyrażenie regularne to (\S+)(. = ).(.+)}, które pasuje do wszystkiego oprócz typu (w tym spacji końcowej) i końcowego średnika. Korzystając z pierwszego przykładu z pytania, grupy przechwytujące otrzymują foo[:] = i4, 8, 15, 16, 23, 42 .

Zastąpienie jest wartością zwracaną funkcji bez nazwy {[b#Yd^k']';.n.b.,#y.c.y]}, która jest wywoływana z całym dopasowaniem plus grupy przechwytywania jako argumenty. Zatem w ramach funkcji bpobiera grupę przechwytywania 1, cgrupę 2 id grupę 3.

Budujemy listy, pierwsze trzy pozycje, które będą "foo[", 6i "]". Aby uzyskać 6, podzieliliśmy dsię na wbudowaną zmienną k= ", ", Yprzekartkowaliśmy wynikową listę liczb całkowitych na yzmienną do przyszłego wykorzystania, i wzięliśmy długość ( #).']to dosłowny charakter.

Pozostaje zbudować serię ciągów formy ";\nfoo[i] = x". Aby to zrobić, możemy złączyć co następuje: ';, n(wbudowany do nowej linii), b(grupa 1-ty capture), ,#y(odpowiednik Python range(len(y))), c(grupa 2-ty capture), a y. Łączenie działa itemowo na listach i zakresach, więc wynikiem jest lista ciągów. Podsumowując, zwracaną wartością funkcji będzie lista taka jak ta:

["foo[" 6 "]"
 [";" n "foo[" 0 "] = " 4]
 [";" n "foo[" 1 "] = " 8]
 [";" n "foo[" 2 "] = " 15]
 [";" n "foo[" 3 "] = " 16]
 [";" n "foo[" 4 "] = " 23]
 [";" n "foo[" 5 "] = " 42]
]

Ponieważ ta lista jest używana w Rzastępowaniu ciągów , jest ona domyślnie rzutowana na ciąg. Domyślna konwersja list-to-string w Pip łączy wszystkie elementy:

"foo[6];
foo[0] = 4;
foo[1] = 5;
foo[2] = 15;
foo[3] = 16;
foo[4] = 23;
foo[5] = 42"

Ostatecznie wynik (w tym typ i końcowy średnik, które nie zostały dopasowane przez wyrażenie regularne, a zatem pozostają niezmienione) jest drukowany automatycznie.


4

Perl 5.10, 73 72 68 66 + 1 (dla przełącznika -n) = 67 bajtów

perl -nE '($t,$n,@a)=/[-[\w]+/g;say"$t $n".@a."];";say$n,$i++,"] = $_;"for@a'

To miłe wyzwanie dla Perla i jak najkrótsze spośród języków ogólnego przeznaczenia. Równoważny

($t, $n, @a) = /[-[\w]+/g;
say "$t $n" . @a . "];";
say $n, $i++, "] = $_;" for @a;

4

PowerShell v2 +, 114 105 bajtów

$a,$b,$c,$d=-split$args-replace'\[]';"$a $b[$(($d=-join$d|iex|iex).length)];";$d|%{"$b[$(($i++))] = $_;"}

Pobiera ciąg wejściowy $argsi -replacenawias kwadratowy bez niczego, a następnie wykonuje znak -splitspacji. Pierwszy bit przechowujemy w $a, drugi bit w $b, elementy =w $ci elementy tablicy w $d. W poniższym przykładzie przechowuje się foow $ai bardo$b , a cała tablica w $d.

Następnie wyjście z nasza pierwsza linia "$a ..."w środku przekształcić $dz tablicą ciągów postaci {1,, 2,... 100};do zwykłego int tablicy przez -joining go ze sobą w jeden ciąg, a następnie uruchomić go poprzez iexdwa razy (podobnie jak eval). Przechowujemy wynikową tablicę z powrotem $dprzed wywołaniem .lengthmetody w celu wypełnienia odpowiedniej liczby pomiędzy[] wierszem wyjściowym.

Następnie wysyłamy $dza pomocą pętli |%{...}. Każdą iterację wyprowadzamy "$b..."za pomocą zmiennej przeciwnej $izawartej w nawiasach i bieżącej wartości $_. $iZmienna zaczyna niezainicjowanymi (odpowiednik $null), ale ++rzuci go do intprzed wyjściem, więc będzie rozpocząć produkcję na 0wszystko przed zwiększany $ido następnej iteracji pętli.

Wszystkie linie wyjściowe są pozostawione w potoku, a dane wyjściowe do terminala są niejawne przy zakończeniu programu.

Przykład

PS C:\Tools\Scripts\golfing> .\expand-a-c-array.ps1 "foo bar[] = {1, 2, 3, -99, 100};"
foo bar[5];
bar[0] = 1;
bar[1] = 2;
bar[2] = 3;
bar[3] = -99;
bar[4] = 100;

Uff! Udało mi się zdobyć odpowiedź Ruby na twoje, biorąc pod uwagę twój komentarz na temat pokonania innych nie-esolangów! Dobra robota, +1.
— Wartość tuszu

@KevinLau Thanks! Wracam do ciebie z 105 teraz. ;-)
— AdmBorkBork

Zadzwonię do twojego 105 i podniosę ci 99! : D
— Wartość tuszu

Już nie zbliża się do pokonania Retiny.
— CalculatorFeline

3

DO, 278 280 bajtów

grał w golfa:

x,e,l,d;char *m,*r,*a;char i[999];c(x){return isdigit(x)||x==45;}main(){gets(i);m=r=&i;while(*r++!=32);a=r;while(*++r!=93);l=r-a;d=r-m;for(;*r++;*r==44?e++:1);printf("%.*s%d];\n",d,m,e+1);r=&i;while(*r++){if(c(*r)){m=r;while(c(*++r));printf("%.*s%d] = %.*s;\n",l,a,x++,r-m,m);}}}

bez golfa:

/* global ints
 * x = generic counter
 * e = number of elements
 * l = length of the array type
 * d = array defination upto the first '['
 */
x,e,l,d;
/* global pointers
 * m = memory pointer
 * r = memory reference / index
 * a = pointer to the start of the array type string
 */
char *m,*r,*a;
/* data storage for stdin */
char i[999];
c(x){return isdigit(x)||x=='-';}
main(){
    gets(i);
    m=r=&i;
    while(*r++!=32);                // skip first space
    a=r;
    while(*++r!=93);                // skip to ']'
    l=r-a;
    d=r-m;
    for(;*r++;*r==44?e++:1);        // count elements
    printf("%.*s%d];\n",d,m,e+1);   // print array define
    r=&i;
    while(*r++) {                   // print elements
        if(c(*r)) {                 // is char a - or a digit?
            m=r;
            while(c(*++r));         // count -/digit chars
            printf("%.*s%d] = %.*s;\n",l,a,x++,r-m,m);
        }
    }
}

Podczas pracy nad tym ktoś opublikował krótszą wersję używającą sscanf do analizowania zamiast używania wskaźników danych ... ładna!

AKTUALIZACJA: Wykryto brakujące spacje wokół równych w drukowanym elemencie, internetowy link IDE: http://ideone.com/KrgRt0 . Uwaga: ta implementacja obsługuje liczby ujemne ...


2

Awk, 101 bajtów

{FS="[^[:alnum:]_-]+";printf"%s %s[%d];\n",$1,$2,NF-3;for(i=3;i<NF;i++)printf$2"[%d] = %d;\n",i-3,$i}

Bardziej czytelnie:

{
FS="[^[:alnum:]_-]+"
printf "%s %s[%d];\n", $1, $2, NF - 3
for (i=3; i < NF; i++)
    printf $2"[%d] = %d;\n", i-3, $i
}
  • Ustawiam separator pól na wszystko oprócz alfabetów, cyfr, znaku podkreślenia i -. Tak więc pola byłyby nazwą typu, nazwą zmiennej i liczbami.
  • Liczba pól będzie wynosić 1 (dla typu) + 1 (dla nazwy) + N (liczby) + 1 (puste pole po trailingu };). Rozmiar tablicy to NF - 3.
  • Następnie drukuje specjalny wiersz deklaracji i zapętla liczby.
  • I należy przypisać FSzarówno podczas wywoływania awk (za pomocą -F) albo w BEGINbloku. W trosce o zwięzłość….

1
W rzeczywistości FSnależy go przypisać albo BEGINużyć, -Finaczej nie zostanie użyty do podzielenia pierwszego wiersza, a ponieważ jest tylko 1 wiersz danych wejściowych ...
— Robert Benson

@RobertBenson masz rację, więc polecenie brzmiałoby awk '-F[^[:alnum:]_-]+' '{printf"%s %s[%d];\n",$1,$2,NF-3;for(i=3;i<NF;i++)printf$2"[%d] = %d;\n",i-3,$i}'102 bajtów, nie licząc awksię. Hmmm. Czy mogę wykluczyć cytaty?
— muru

Tak, możesz wykluczyć cytaty. Czasami podajesz go jako C+O bytesgdzie Ci Oreprezentujesz bajty odpowiednio z kodu i opcji. Oczywiście na ogół używam tylko BEGINbloku, więc nie muszę o tym myśleć. : p
— Robert Benson

2

JavaScript ES6, 134 132 130 129 bajtów

Zapisano 1 bajt dzięki Neilowi.

x=>(m=x.match(/(\w+) (\w+).+{(.+)}/),m[1]+` `+(q=m[2])+`[${q.length-1}];
`+m[3].split`, `.map((t,i)=>q+`[${i}] = ${t};`).join`
`)

Nie powinno `[${i}] = `+t+";"być `[${i}] = ${t};`?
— Neil

@Neil Thanks, zapisany bajt!
— Conor O'Brien

2

bash, 133 129 bajtów

read -a l
d="${l[@]:0:2}"
e=("${l[@]:3}")
echo "${d%?}${#e[@]}];"
for i in "${!e[@]}"
{
echo "${l[0]}[$i] = ${e[$i]//[!0-9]/};"
}

Pierwsza próba, na pewno można ją skrócić.


2

D, 197,188 bajtów

import std.array,std.stdio;void main(){string t,n,e;readf("%s %s] = {%s}",&t,&n,&e);auto v=e.replace(",","").split;writeln(t,' ',n,v.length,"];");foreach(i,c;v)writeln(n,i,"] = ",c,";");}

lub bez golfa:

import std.array, std.stdio;

void main() {
    string type, nameAndBracket, elems;
    readf("%s %s] = {%s}", &type, &nameAndBracket, &elems);

    // remove all commas before splitting the string into substrings
    auto vector = elems.replace(",","").split();

    // writeln is shorter than fln by 1 char when filled in
    writeln(type, ' ', nameAndBracket, vector.length, "];");

    // print each element being assigned
    foreach(index, content; vector)
        writeln(nameAndBraket, index, "] = ", content, ";");
}

Nie znam D, ale czy mógłbyś odczytać otwierający nawias kwadratowy jako część nazwy? Pozwoliłoby to zaoszczędzić konieczności późniejszego pisania nawiasu kwadratowego.
— DLosc

2

Julia, 154 134 101 bajtów

f(s,c=matchall(r"-?\w+",s),n=endof(c)-2)=c[]" "c[2]"[$n];
"join([c[2]"[$i] = "c[i+3]";
"for i=0:n-1])

Jest to funkcja, która akceptuje ciąg i zwraca ciąg z pojedynczym końcowym znakiem nowej linii.

Nie golfowany:

function f(s, c = matchall(r"-?\w+", s), n = endof(c) - 2)
    c[] " " c[2] "[$n];\n" join([c[2] "[$i] = " x[i+3] ";\n" for i = 0:n-1])
end

Definiujemy, cże jest tablicą dopasowań danych wejściowych wyrażenia regularnego -?\w+. Uwzględnia typ, nazwę tablicy, a następnie każdą wartość. Przechowujemy njako długośćc - 2, która jest liczbą wartości. Dane wyjściowe są konstruowane jako interpolowany ciąg typu, nazwy i długości, połączony z każdą linią definicji oddzieloną znakami nowej linii. Z jakiegokolwiek powodu c[]jest taki sam jak c[1].

Zapisano 32 bajty z pomocą Dennisa!


1

Python 2, 159 bajtów

s=input().split()
t,n,v=s[0],s[1][:-2],''.join(s[3:])
a=v[1:-2].split(',')
print'%s %s[%d];'%(t,n,len(a))
for i in range(len(a)):print'%s[%d] = %s;'%(n,i,a[i])

Wypróbuj online

Dzięki Kevin Lau za sugestie dotyczące gry w golfa


1

Python 3, 116 bajtów

t,v,_,*l=input().split();v=v[:-1]+'%s]'
print(t,v%len(l)+';');i=0
for x in l:print(v%i,'= %s;'%x.strip('{,};'));i+=1

Dzieli dane wejściowe na typ, nazwę i listę liczb. Po wydrukowaniu deklaracji macierzy drukuje elementy, ręcznie wyliczając liczby, usuwając nadmiar interpunkcji dołączonej do pierwszej i ostatniej.

Inne podejście w Pythonie 2 wyszło na 122 bajty:

a,b=input()[:-2].split('] = {')
l=eval(b+',')
print a+`len(l)`+"];"
for y in enumerate(l):print a.split()[1]+'%s] = %s;'%y

Chodzi o evallistę liczb jako krotkę z przecinkiem na końcu, aby pojedynczy numer był rozpoznawany jako typ. Wymieniona lista liczb zawiera krotki w formacie ciągu.


1

PHP, 143 bajty

Grał w golfa

<?$t=count($n=explode(' ',preg_replace('/[^\s\w]/','',$argv[1])))-3;echo"$n[0] {$n[1]}[$t];";for($i=2;$t>$j=++$i-3;)echo$n[1]."[$j] = $n[$i];";

Bez golfa

<?  
$t = count(                                  // Get the number of elements for our array...
    $n = explode(' ',                            // After split the input on whitespace...
    preg_replace('/[^\s\w]/','',$argv[1])))-3;  // After removing all special characters.
echo "$n[0] {$n[1]}[$t];";                     // First line is type, name, and count.
for($i=2;                                        // Loop through array elements
    $t > $j = ++$i-3;)                         // Assign j to be the actual index for our new array
    echo $n[1]."[$j] = $n[$i];";                // Print each line

Dane wejściowe są pobierane za pomocą argumentu wiersza poleceń. Próba:

C:\(filepath)>php Expand.php "int foo[] = {4,8,15,16,23,42};"

Wydajność:

int foo[6];foo[0] = 4;foo[1] = 8;foo[2] = 15;foo[3] = 16;foo[4] = 23;foo[5] = 42;

0

MATL , 68 64 58 bajtów

'\w+'XX2:H#)XKxXIZc'['KnV'];'v!K"I2X)'['X@qV'] = '@g';'6$h

To nie jest C, ale używa sprintffunkcji podobnej do C Nah, która marnowała 4 bajty.

Wypróbuj online!

          % Take input implicitly
'\w+'XX   % Find substrings that match regex '\w+'. Gives a cell array
2:H#)     % Split into a subarray with the first two substrings (type and name), and 
          % another with the rest (numbers that form the array)
XKx       % Copy the latter (numbers) into clipboard K. Delete it
XI        % Copy the former (type and name) into clipboard I
Zc        % Join the first two substrings with a space
'['       % Push this string
K         % Paste array of numbers
nV        % Get its length. Convert to string
'];'      % Push this string
v!        % Concatenate all strings up to now. Gives first line of the output
K"        % For each number in the array
  I2X)    %   Get name of array as a string
  '['     %   Push this string
  X@qV    %   Current iteration index, starting at 0, as a string
  '] = '  %   Push this string
  @g      %   Current number of the array, as a string
  ';'     %   Push this string
  5$h     %   Concatenate top 6 strings. This is a line of the output
          % Implicity end for each
          % Implicitly display

0

Clojure, 115 bajtów

#(let[[t n & v](re-seq #"-?\w+"%)](apply str t" "n\[(count v)"];\n"(map(fn[i v](str n"["i"] = "v";\n"))(range)v))))

Nie byłem w stanie ładnie połączyć awful_array_name[5];i awful_array_name[0] = 7;części, aby ponownie użyły kodu: /

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.