Matematyka jest faktem. Programowanie nie jest

175

W matematyce wykrzyknik !często oznacza silnię i pojawia się po kłótni.

W programowaniu wykrzyknik !często oznacza negację i pojawia się przed argumentem.

W przypadku tego wyzwania zastosujemy te operacje tylko do zera i jednego.

Factorial
0! = 1
1! = 1

Negation
!0 = 1
!1 = 0

Weź ciąg zerowy lub więcej !, następnie 0lub 1, a następnie zero lub więcej !( /!*[01]!*/).
Na przykład wejściem może być !!!0!!!!lub !!!1lub !0!!lub 0!lub 1.

!„S przed 0lub 1są negacji i !” s po są silni.

Silnia ma wyższy priorytet niż negacja, więc silnie są zawsze stosowane jako pierwsze.
Na przykład !!!0!!!!naprawdę oznacza !!!(0!!!!), albo jeszcze lepiej !(!(!((((0!)!)!)!))).

Wyprowadza wynikowe zastosowanie wszystkich silni i negacji. Wyjście będzie zawsze 0lub 1.

Przypadki testowe

0 -> 0
1 -> 1
0! -> 1
1! -> 1
!0 -> 1
!1 -> 0
!0! -> 0
!1! -> 0
0!! -> 1
1!! -> 1
!!0 -> 0
!!1 -> 1
!0!! -> 0
!!!1 -> 0
!!!0!!!! -> 0
!!!1!!!! -> 0

Najkrótszy kod w bajtach wygrywa.

Hobby Calvina
źródło
18
Ale 0! = 1 !, więc jaki jest sens obsługi wielu silni?
Boboback
30
@boboquack Ponieważ to jest wyzwanie.
Hobby Calvina,
11
<? = „1”; ... poprawia 75% czasu w php.
azyl
10
Mogę się tutaj mylić, ale czy żadna liczba z dowolnymi silnikami nie jest po prostu usunięta i zastąpiona 1? Jak 0 !!!! = 1 !! = 0 !!!!!!!! = 1 !!! = 1! = 0! = 1 itd.
Albert Renshaw
2
@AlbertRenshaw To prawda.
Calvin's Hobbies,

Odpowiedzi:

43

Mathematica, 25 17 bajtów

Input[]/.!x_:>1-x

Pobiera dane z monitu użytkownika. Zakłada środowisko notebooka Mathematica do niejawnego drukowania. Aby uczynić go skryptem wiersza poleceń, zawiń go Print[...]lub uczyń z niego funkcję bez argumentów (która następnie pobiera dane z wiersza poleceń), dołącz &.

Mathematica ma oba wymagane operatory (z wymaganym pierwszeństwem), więc możemy po prostu „ewaluować” dane wejściowe (co jest wykonywane automatycznie Input[]), ale operator logicznej negacji nie działa na liczbach całkowitych (więc pozostanie nieoceniony). Jeśli wynik !xpozostanie, zamieniamy go na 1-x.

Kilka zabawnych faktów na temat oceny:

  1. Mathematica faktycznie ma również podwójny operator czynnikowy !!, który oblicza n*(n-2)*(n-4)*..., ale stosuje się 0lub 1nadal daje 1, więc nie ma znaczenia, że 0!!!!!tak naprawdę zostanie on przeanalizowany jako ((0!!)!!)!.
  2. Mimo że Mathematica odchodzi !0i jest !1nieoceniony, wie, że !jest on odwrotny, więc automatycznie anuluje wszystkie pary prowadzenia !. Po ToExpressionjesteśmy zawsze pozostaje jednym z 0, 1, !0, !1.
Martin Ender
źródło
3
Od kiedy domyślnie dozwolony jest fragment REPL?
LegionMammal978
2
@ LegionMammal978 Najwyraźniej od grudnia 2015 r., Ale ciągle o tym zapominam. Szczerze mówiąc, nie jest to „fragment”, ponieważ nie zakłada, że ​​dane wejściowe są już zapisane w pamięci. Zakładając, że środowisko notebooka nie różni się zbytnio od posiadania języka z niejawnym wynikiem.
Martin Ender,
Ciekawe, czy można podać meta link? (Próba znalezienia informacji jest stresująca, to kolejny problem formatu pytań i odpowiedzi na SE ...)
LegionMammal978
@ LegionMammal978 jest już w odpowiedzi.
Martin Ender,
Czyste rozwiązanie ksh x=${x/[01]!*/1};echo $(($x))- nie można opublikować poprawnej odpowiedzi :(
DarkHeart
28

[Bash] + narzędzia Unix, 21 17 bajtów

sed s/.!!*$/1/|bc

To musi być zapisane w pliku i uruchomić jako program. Jeśli spróbujesz wprowadzić polecenie bezpośrednio z wiersza polecenia, nie zadziała, ponieważ !! jest rozszerzany z powodu włączenia podstawiania historii w trybie interaktywnym bash. (Alternatywnie możesz wyłączyć podstawianie historii za pomocą set +H.)

Uruchamianie przypadku testowego:

for x in 0 1 '0!' '1!' '!0' '!1' '!0!' '!1!' '0!!' '1!!' '!!0' '!!1' '!0!!' '!!!1' '!!!0!!!!' '!!!1!!!!'; do ./excl <<<"$x"; done

0
1
1
1
1
0
0
0
1
1
0
1
0
0
0
0
Mitchell Spector
źródło
Stara wersja działa, ta nie
krowy szarlatają
Użyłem linku TIO
szarlatan krów
@KritixiLithos Działało dobrze, kiedy próbowałem go na moim Linux-ie. Problem polegał na tym, że TIO wymaga nowej linii na końcu symulowanej linii wejściowej. To myląca sytuacja, więc wyjąłem link TIO. Jeśli chcesz go wypróbować, oto link ponownie (ale pamiętaj o dodaniu
Mitchell Spector
2
Ale co, jeśli ktoś uciekł mkdir -p 's/.!!'{bunch,of,different,directories}\$/1? Następnie otrzymasz Pathname Expansion, a Sed będzie próbował czytać katalogi tak, jakby były plikami, zamiast czytać standardowe dane wejściowe i nic nie wyświetli! :)
Wildcard,
1
@Wildcard Zgadzam się całkowicie. W skryptach produkcyjnych zawsze używam cudzysłowów w takich sytuacjach. (W tym przypadku faktycznie wstawiłbym podwójny cudzysłów wokół argumentu sed, zamiast po prostu uciekać przed *. Łatwiej jest go czytać niż używać ukośników odwrotnych i unika się możliwości pominięcia jakiegoś specjalnego znaku.)
Mitchell Spector
22

Siatkówka , 20 15 14 bajtów

Dzięki Leo za oszczędność 1 bajtu.

0!
1
!!

^1|!0

Wypróbuj online!

Wyjaśnienie

0!
1

Zamień się 0!w 1. Nie obchodzą nas żadne inne końcowe !, wynikowa liczba jest taka sama, jakbyśmy zastosowali wszystkie silnie.

!!

Anuluj pary negacji. Może to również anulować niektóre czynniki, ale to nie ma znaczenia.

^1|!0

Policzyć liczbę meczów tego regex, który jest albo 1czy 0i daje pożądanego rezultatu.

Martin Ender
źródło
Alternatywne rozwiązanie dla tego samego bajtu: \d.+...
Krowy szarlatają
@KritixiLithos Znalazłem sposób, aby całkowicie tego uniknąć.
Martin Ender,
Możesz usunąć ^wcześniej!0
Leo
17

Brud , 14 12 9 bajtów

e`\0!~\!_

Wypróbuj online!

Wyjaśnienie

Dopasowuje dane wejściowe do wzorca, drukując 1dla dopasowania i 0bez dopasowania.

e`\0!~\!_
e`         Match entire input against this pattern:
    !      not
  \0       a sole 0
     ~     xor
      \!   exclamation mark
        _  followed by this pattern matched recursively.

Chodzi o to, że. Jeśli dane wejściowe zaczynają się od cyfry, część rekurencyjna \!_zawsze kończy się niepowodzeniem i \0!kończy się powodzeniem, chyba że mamy jedną 0. Ich xor się powiedzie, chyba że dane wejściowe są pojedyncze 0. Jeśli dane wejściowe zaczynają się od !, to \0!zawsze się powiedzie, i\!_ kończy się powodzeniem, jeśli dopasowanie rekurencyjne się powiedzie. Ich xor odnosi sukces dokładnie wtedy, gdy dopasowanie rekurencyjne kończy się niepowodzeniem, co neguje je.

Zgarb
źródło
16

Brainfuck, 85 72 (84) bajtów

,[>-[-----<->]<++[>++++[-<++++>]+<[[+],[[-]>-<]]]>[<<+[-->]>[<],>-]<]<+.

wrócić liczbowo lub

,[>-[-----<->]<++[>++++[-<++++>]+<[[+],[[-]>-<]]]>[<<+[-->]>[<],>-]<]-[-----<+>]<--.

dla tekstu ASCII. > może być także poprzedzony, aby uniknąć zawijania pamięci.

Wypróbuj online!


Loops over the input.
On 1, ends.
On "!", toggles bool a stored as 0 or 255.
On "0", toggles if there is no trailing bit, then ends.

Memory labels  | BOOL | INPUT | FLAG |

,                   first input 
[                     # loop on INPUT
  >-[-----<->]<++     subtract 49 == "1"

  [                     # case not "1"
    >++++[-<++++>]      add 16 since 49 take 16 == "!"

    +                   set FLAG
    <                   move to INPUT
    [                     # case "0"
      [+],                clear and new INPUT
      [                     # case "0!"
        [-]>-<              clear INPUT and FLAG
      ]
    ]
  ]

  >                   move to FLAG
  [                     # case "!" or "0" without tail
    <<+[-->]>[<]        not the BOOL
    ,                   take new input
    >-                  clear FLAG
  ]
  <                   move to INPUT
]

+.                    return 0 or 1

Lub w przypadku odpowiedzi tekstowej zamień ostatni wiersz na

-[-----<+>]<--.       add 49 for "0" or "1" conversion and return
Groby Ruperta
źródło
14

Brainfuck - droga do wielu bajtów (232 bajty)

Wyraźnie niewłaściwy język do wygrywania w golfa kodu. Głównie zauważyłem brak osób korzystających z tego esolangu. Istnieje dobry interpreter bf online lub możesz naprawdę zobaczyć, co program robi za pomocą tego wizualizatora bf .

>>>>>,[>+++[<---------------->-]<<<<<<[-]+>[-]>>>>[-[<<[>+<<<<->>>[<<+>>-] ]<<[>>+<<-]<[>>+<<[-]]>>>>>[-]]<<<<<[>>>++<<<-]>+>>>>[-]]<<<<-[>>+<<[-]]>>>>,]<<->[<[-]+>[-]]<<[<[-]>>[<<+>>[-]]+<<[->>-<<]>-]>>[-]+++[<++++++++++++++++>-]<.
CodyCode
źródło
3
Szalony człowiek !!
Almo
Uwielbiam to, możesz to zrobić w malbolge? XD
Stefan Nolde
Informacja: Poniżej znajduje się zbyt wiele krótszych rozwiązań.
user202729,
14

Python, -44- 42 bajty

Zaoszczędź 2 bajty dzięki Zgarb!

lambda x:(x[-1]=='0')^len(x.rstrip('!'))%2

Krok po kroku:

  1. x[-1]!='0'
    jeśli xkończy się na 1lub !xnie kończy się na 0, część silnia musi mieć wartość 1, w przeciwnym razie0
  2. ^len(x.rstrip('!'))%2
    wykorzystuj własność Xora jako „warunkowo nie”. Warunkiem jest w tym przypadku, jeśli długość początkowego !s jest nieparzysta. Jednak .rstripnie usuwa liczby z łańcucha, więc obliczona długość jest przesunięta o 1, dlatego warunek jest odwrócony
  3. Przesunięcie o 1 w kroku 2 jest korygowane poprzez zmianę !=na ==w kroku 1. Zgarb zasugerował użycie operatora porównania różnic zamiast stosowania innej inwersji, oszczędzając 2 bajty.

Wypróbuj online!

busukxuan
źródło
Nie działa na wejściu !!0; obecnie powraca 1.
Wartość tuszu
@ValueInk powinien już działać
busukxuan
1
lambda x:(x[-1]=='0')^len(x.rstrip('!'))%2unika dodatkowej inwersji.
Zgarb
15
przekreślony 44 jest nadal regularny 44
Rɪᴋᴇʀ
3
Myślę, że twierdzi, że przekreślona 44 czcionka nie wygląda na przekreśloną ... :) Przekreślona część pokrywa się z poziomą częścią 4s.
JeffC,
13

JavaScript (ES6), 43 41 29 bajtów

s=>+eval(s.replace(/.!+$/,1))

Metoda niepregexowa ( 41 31 bajtów)

Poniżej znajduje się moje wstępne podejście. Jest to nieco bardziej interesujące, ale znacznie dłuższe, wciąż nieco dłuższe, nawet po znaczącej optymalizacji przez Neila (10 bajtów zapisanych) .

f=([c,...s])=>1/c?c|s>'':1-f(s)

Przypadki testowe

Arnauld
źródło
Mogę zapisać tylko 10 bajtów z Twojego non-regex metody, więc to wciąż zbyt długi: f=([c,...s])=>1/c?c|s>'':1-f(s).
Neil
@ Neil Ponieważ i tak jest to znacznie lepsze niż moja pierwsza próba, pozwoliłem sobie na uwzględnienie twojej sugestii.
Arnauld
Ha, miałem ten sam pomysł, ale lepiej grałeś w golfa. :)
Devsman
11

Galaretka , 5 bajtów

VeMḂ$

Wypróbuj online!

Funkcja monadyczna oczekująca łańcucha. Wejścia z wiodącymi !s powodują, że 1po drodze drukowane jest STDOUT, więc łącze TIO, które podaję, jest wiązką testową, która drukuje pary wejścia-wyjścia poniżej pierwszego wiersza wyjścia.

W jaki sposób?

VeMḂ$ - Monadic link: string
V     - eval the string
          - the implicit input of 0 causes !...! to evaluate to 1 (which gets printed),
          - the result is the evaluation of the rest: "0"=0; "0!"=1; "1"=1; "1!"=1; ...
 e    - exists in?
    $ - last two links as a monad:
  M   -     Maximal indexes - the "0" and "1" characters are greater than "!",
                            - so this results in a list of one item [i] where
                            - i is the 1-based index of the 0 or 1 character.
   Ḃ  -     %2 (vectorises) - [i%2], so a 0 if we need to logically negate and a 1 if not
                            - hence we check equality with e rather than inequality.
Jonathan Allan
źródło
10

05AB1E , 9 bajtów

Kod:

.V¹'!ÜgG_

Wykorzystuje kodowanie CP-1252 . Wypróbuj online! lub Zweryfikuj wszystkie przypadki testowe!

Wyjaśnienie:

.V         # Evaluate the input as 05AB1E code. This computes the factorial part.
   '!Ü     # Remove trailing exclamation marks..
  ¹        # ..from the first input
      g    # Get the length of the resulting string
       G   # Do the following length - 1 times:
        _  #   Negate the number
Adnan
źródło
10

Siatkówka , 13 bajtów

To trochę dziwne podejście, ale jest krótkie i działa.

0$
!1
!!

^\d

Z pierwszych dwóch liniach zastąpić końcówką 0z !1: z tej wymianie teraz wiemy, że część naszego łańcucha od cyfry roku jest równa 1.

W następnych dwóch wierszach usuń pary !: podwójna negacja usuwa się, a już uwzględnialiśmy silnię w poprzednim kroku.

W ostatnim wierszu dopasuj cyfrę na początku ciągu i zwróć liczbę dopasowań: jeśli wszystkie negacje zostaną wyeliminowane, znajdziemy dopasowanie (i jak powiedzieliśmy wcześniej, wiemy, że jest równe 1), jeśli nadal istnieje zaprzeczenie to nie będzie pasować.

Wypróbuj online!

Lew
źródło
1
Czy ostatnia cyfra niekoniecznie zawsze będzie 1? W takim przypadku możesz użyć 1zamiast \d.
1
@ ais523 nie, ponieważ pierwsza część zastąpi tylko końcowe 0, więc na przykład dane wejściowe 0!pozostaną niezmienione do ostatniej linii
Leo
1
Naprawdę cudowne rozwiązanie, dobra robota! :)
Martin Ender,
10

Rubinowy, 12 + 1 = 39 24 15 13 bajtów

Używa -nflagi. Dzięki @GB za -9 bajtów!

p~/!*$|0$/%2
Wartość tuszu
źródło
Ponieważ sprawdzasz tylko długość, możesz usunąć końcowe zero, zamiast najpierw sprawdzać „! 0”, a potem pojedyncze zero.
GB
@GB to wspaniały pomysł! Znalazłem jednak rozwiązanie, które jest jeszcze krótsze, modyfikując moje wyrażenie regularne, aby szukało pozycji 0 lub końca linii
tusz wartościowy
Następnie możesz po prostu sprawdzić, czy końcowe! lub zero lub koniec wiersza: p ~ /! + $ | 0 $ | $ /% 2 to tylko 14 bajtów.
GB
A następnie „0 $ | $” może stać się „0? $”, Aby zapisać kolejny bajt.
GB
1
Lepiej jeszcze !*$jest krótszy o dwa!
Wartość tuszu
9

Perl , 20 bajtów

19 bajtów kodu + -pflaga.

s/\d!+/1/;$_=0+eval

Wypróbuj online!

Powraca negacja Perl undeflub 1, więc używam 0+do numerify wynikowe 0+undefzyski 0. Poza tym niewiele można powiedzieć o kodzie.

Dada
źródło
2
Właśnie to napisałem. Masz +1.
primo
@primo Cieszę się, że choć raz nie jestem za tobą 20 bajtów! Dzięki :)
Dada
9

C, 68 62 61 53 bajtów

c;e(char*a){for(c=1;*a<34;a++)c^=1;c=a[1]?c:*a&1^!c;}

Wyciągnęliśmy jeszcze kilka bajtów z pewnym nadużyciem

Wypróbuj online!

Ahemone
źródło
1
Myślę, że można usunąć intz funkcji i można zmienić *a==33się *a<34.
Krowy szarlatan
Niestety *a%2jest krótszy niż*a-48
krowy szarlatan
Dzięki za wskazówkę. Byłem także w stanie wyeliminować inną postać, usuwając nawiasy wokół powrotu i przypisując go.
Ahemone
Jestem pewien, że for(;*a<34;a++)można skrócić do for(;*a++<34;)zapisania 1 bajtu
Albert Renshaw
Niestety nie, jako instrukcja warunkowa, zawsze będzie ona wykonywana, a więc przesunie wskaźnik zbyt daleko w przód, aby dereferencja była zwracana.
Ahemone
6

Perl 6 , 32 28 23 bajtów

{m/(\!)*(1|0.)*/.sum%2}

Jak to działa

{                     }  # A lambda.
{m/            /      }  # Match the lambda argument against the regex:
   (\!)*                 #   Zero or more `!`.
                         #     (First capture will be an array with one element per negation).
        (1|0.)*          #   A `1`, or a `0` and another character, zero or more times.
                         #     (Second capture will be a one-element array if the factorial
                         #     part evaluates to 1, and an empty array otherwise.)
                .sum     # Add the lengths of the two captures,
                    %2   # and return that sum modulo 2.
smls
źródło
6

Haskell , 39 bajtów

f('!':b)="10"!!read[f b]
f[a]=a
f _='1'

Definiuje funkcję f, która pobiera ciąg znaków i zwraca znak. Wypróbuj online!

Wyjaśnienie

Istnieją trzy przypadki: dane wejściowe zaczynają się od !, dane wejściowe mają długość 1 i wszystko inne.

f('!':b)=    -- If input has head '!' and tail b,
 "10"!!      -- we index into the string "10"
  read[f b]  -- using f b converted to int. This essentially inverts f b.
f[a]=        -- If input has only one character, we know it's a digit,
 a           -- so we can just return it.
f _=         -- In all other cases, we know the input is a digit followed by !s,
 '1'         -- so we can return '1'.
Zgarb
źródło
Przełączyć się z String do Integer jako zwracanego typu: f('!':b)=[1,0]!!f b;f"0"=0;f _=1.
nimi
6

Befunge, 24 bajty

~"!"-:#v_$1+
*+2%!.@>0~`

Wypróbuj online!

Zaczyna się od zliczenia !znaków odczytanych ze standardowego wejścia. Pierwszym znakiem, który nie jest a, !będzie albo, 0albo 1, ale w trakcie testowania !odejmiemy 33, czyli 15 lub 16. Następnie odczytujemy jeszcze jeden znak, który będzie albo !EOF, i porównaj, jeśli jest to mniej niż 0 (tj. EOF).

Biorąc te trzy punkty danych - liczbę wykrzykników ( c ), wartość cyfr, ( d ) i warunek końca pliku ( e ) - możemy obliczyć wynik w następujący sposób:

!((c + d*e) % 2)

Pomnożenie wartości cyfry przez warunek końca pliku oznacza, że ​​zostanie zamieniona na zero, jeśli po cyfrze pojawi się a !, co da jej tę samą wartość modulo 2 co 1((pamiętaj, że została przekonwertowana na 16). Ale przed zastosowaniem modulo 2 dodajemy początkową liczbę wykrzykników, która skutecznie przełącza wynik modulo 2 tyle razy, ile było ich !prefiksów. I w końcu nie jesteśmy wynikiem, ponieważ nasze wartości podstawowe są 0i 1są przeciwieństwem tego, czego potrzebujemy.

Bardziej szczegółowe spojrzenie na kod:

~                Read a character from stdin.
 "!"-            Subtract 33 (ASCII for '!').
     :  _        Make a duplicate and check if zero (i.e. is it a '!').
         $1+     If so, drop the duplicate, increment a counter, and repeat.
       v         Otherwise move to the second line, leaving the digit value on the stack.
       >0~`      Read one more character and check if less than 0 (i.e. EOF).
*                Multiple by the digit value, making it zero if not followed by EOF.
 +               Add to the exclamation count.
  2%             Modulo 2 the result.
    !            Then not that value.
     .@          And finally write to stdout and exit.
James Holderness
źródło
6

Haskell , 27 bajtów

f('!':b)=1-f b
f"0"=0
f _=1

Wypróbuj online!

Każda interlinia !uzupełnia wynik dla reszty wyrażenia, wykonana jako 1-. Ciągle przewracamy, aż trafimy na cyfrę. Jeśli reszta jest równa "0", wynikiem jest 0. W przeciwnym razie, to a 1lub następuje jeden lub więcej !, więc wynik to 1.

xnor
źródło
5

Rubin, 22 21 20 bajtów

->s{(s=~/!*$|0$/)%2}

Wyjaśnienie:

  • Pierwszy przypadek, mam trochę „!” na koniec usuń je, uzyskaj długość modulo 2.
  • Drugi przypadek, brak „!”, Jeśli ostatni znak ma wartość zero, usuń go, uzyskaj długość modulo 2
  • Jeśli ostatnim znakiem jest 1, wróć do pierwszego przypadku

(-1 bajt kradnący pomysł @Value Ink)

GB
źródło
Wspaniale, patrzyłem na tę układankę przez 10 minut, ale nie miałem dużo czasu, a potem o niej zapomniałem. Teraz zauważyłem to ponownie w aktywnych pytaniach i byłem zachwycony, widząc takie miłe podejście.
akostadinov
4

Galaretka , 8 bajtów

œr”!LḂ=V

Wypróbuj online!

Jest to funkcja (łącze monadyczne), która pobiera jeden argument i zwraca wartość zwrotną. (Często zapisuje śmieci na standardowe wyjście jako efekt uboczny, ale nas to nie obchodzi.)

Wyjaśnienie

œr”!LḂ=V
œr”!      Take {the input}, with all trailing ! deleted
    L     Take the length of this
     Ḃ    Take the parity of that length
      =   Return 0 if unequal, 1 if equal to:
       V    the value of {the input} when eval'ed as a niladic Jelly program

Po pierwsze, zauważ, że ponieważ dane wejściowe zawsze składają się z pewnej liczby !, po której następuje cyfra, a następnie więcej !, że jeśli usuniemy znak końcowy !i przyjmiemy długość, otrzymamy jeden plus liczbę wiodących !w programie. Przyjęcie parzystości zwróci 0, jeśli liczba nieparzysta będzie !, lub 1, jeśli liczba parzysta będzie !. Porównywanie do 0 jest funkcją „nie”, podczas gdy porównywanie do 1 jest funkcją tożsamości; w ten sposób œr”!LḂ=skutecznie wdraża !część pytania „traktuj wiodącą jako operatorów NIE”.

Jeśli chodzi o drugą połowę, obsługa silni !jest operacją silną w Jelly, więc jeśli program nie ma wiodącej funkcji !, możemy rozwiązać problem bezpośrednio za pomocą prostej eval( V). Jeśli program nie posiada wiodącą !, ci będą interpretowane jako biorąc silni 0 (ewentualnie kilka razy), tworząc wartość zwracaną 1, które będą drukowane na standardowe wyjście i wyrzucić raz cyfrą jest widoczne; dlatego nie mają one wpływu na wartość zwracaną funkcji, która jest moim poddaniem się pytaniu.


źródło
Bardzo ładne i świetne wytłumaczenie.
ElPedro,
4

Python, 38 bajtów

lambda s:(s[1::2]>s[::2])^ord(s[-1])%2

TryItOnline!

Nienazwana funkcja pobierająca ciąg wejściowy si zwracająca liczbę całkowitą 0lub 1.

s[1::2] to wycinek ciągu wejściowego, który zaczyna się od indeksu 1 i ma rozmiar kroku dwa:
'Like this' -> 'ieti'

s[::2] jest podobny, ale zaczyna się od domyślnego indeksu 0:
'Like this' -> 'Lk hs'

Test (s[1::2]>s[::2])sprawdza, czy oparty na 0 indeks '0'lub '1'jest nieparzysty, tj. Czy musimy uzupełnić.
Działa to, ponieważ kolejność ciągów jest sprawdzana leksykograficznie z dowolnym niepustym ciągiem większym niż pusty ciąg, a także z kolejnością ASCII, więc '1'>'0'>'!'. Jest to bajt krótszy niż prostszy s.index(max(s))%2.

Do ord(s[-1])%2sprawdza czy ostatni znak nie jest to '0'(dla ważnej wejścia) i skutkuje całkowitą (podczas tej samej długości (s[-1]!='0')zwróci wartość logiczną).
To działa, ponieważ ostatni znak wejścia, s[-1], będzie '0','1' lub '!'które mają odpowiednio punkty 48, 49 i 33 kodu ASCII, które są 0, 1 i 1 modulo 2.

^Następnie wykonuje bitowym operacji LUB wykluczające na dwóch powyższych wartości powrotu liczbę całkowitą od jednego wejściowego, prawą jest liczbą całkowitą. Jeśli lewy ma wartość Prawda, zwracane jest uzupełnienie prawej, jeśli lewe to Fałsz, zwracane jest prawo, zgodnie z wymaganiami.

Jonathan Allan
źródło
4

Java 7, 105 82 81 bajtów

int a(char[]a){int b=0,c=0;for(;a[b++]<34;c^=1);return(b<a.length?1:a[b-1]&1)^c;}

Wypróbuj online!

Stare rozwiązanie wyrażenia regularnego

int a(String a){a=a.replace("0!","1").replaceAll("1.*","1");int b=a.length()-1;return b%2^a.charAt(b)&1;}
Szturchać
źródło
2
c^=1jest super sprytny. To nieużywany operator, jeśli kiedykolwiek go widziałem.
Addison Crump,
3

CJam , 12 11 bajtów

r_W='0=!\~;

Wypróbuj online! Zestaw testowy (drukuje 1dla każdego poprawnego przypadku testowego).

r      e# Read input.
_W='0= e# Duplicate and check whether the string ends in '0'. This is the
       e# only case in which the factorial part results in 0.
!      e# Negate this to get the actual result of the factorial part.
\      e# Swap with the input.
~      e# Evalute the input as CJam code. The leading `!` will apply the logical
       e# negations to the factorial result. The 0 or 1 will then push a junk value
       e# which is potentially negated a few times as well, by the factorials.
;      e# Discard the junk value.
Martin Ender
źródło
3

Haskell , 67 65 bajtów

f s|foldr(\_->not)(last s`elem`"1!")$fst.span(<'0')$s="1"|1<3="0"

Wypróbuj online!Stosowanie:f "!!!0!!!!"

Zaoszczędzono dwa bajty dzięki @nimi.

Laikoni
źródło
3

Brainfuck, 115 bajtów

>,[->++++[<-------->-]<[--------------->,[<[-]+>-]<<[->-[>+<+]>[-<+>]<<]>>++++++[-<++++++++>]<.>>+<]>-[<<+>,>[-]]<]

Wypróbuj online!

Nie golfowany:

% 0: inverter count
% 1: result
% 2: if/else flag; tmpspace in inner loop 0

>1,[
    ->2++++[<-------->-]<1 subtract 33 (!)
    [ 
        % we've reached the number
        ---------------
        % now it's either 0 or 1

        % check next char; If it's not 0 then it's '!'
        % 0! = 1! = 1!...! so we only need to determine if at least one ! exists
        >2,
                [<[-]+>-]<1

        % apply inversions
        <0
        [->1
            % invert cell 1 once each iteration
                       % cell 1 is 0 or 1
            -          % cell 1 is 255 or 1
            [>+<+]     % cell 1 is 0; cell 2 is 1 iff cell 1 should be 1
            >2[-<+>]<1 % cell 1 is 1 or 0
        <0]

        % print result
        >1>++++++[-<++++++++>]<1.

        >>2+< % tape={0 r 0 1}
    ]
    >2-[ % we haven't seen the number yet
        <<0+>1,>2 % add to inverter count
        [-]
    ]<1
]
Promień
źródło
2

Partia, 62 bajty

@set/ps=
@set s=%s:0!=1%
@set s=%s:!!=%
@cmd/cset/a%s:1!=1%

Pobiera dane wejściowe na STDIN. Batch właściwie rozumie wiodące !s dla tego wyzwania, ale końcowe! należy zająć się , co wymaga trzech kroków:

  • Zmień 0!na1
  • Usuń pary !!(jest to bezpieczne dla!! s przed cyfrą)
  • Usuń wszelkie pozostałe końcowe !(które do tej pory mogą być tylko po 1)
Neil
źródło
2

Formuła IBM / Lotus Notes - 77 bajtów

@Eval(@Left(a;@If(@Like(a;"%1%");"1";"0"))+@If(@Ends(a;"!");"1";@Right(a;1)))

Nie ma TIO dla Notes Formula, więc zrzut ekranu wszystkich przypadków testowych pokazano poniżej:

Wszystkie przypadki testowe

Jak to działa

@Eval() ocenia ciąg jako wyrażenie

Najpierw sprawdzamy, czy ciąg wejściowy w polu (wejście) azawiera 1lub 0zabiera wszystkie znaki po lewej stronie, zależnie od tego, który to ciąg !znaków. Nie obchodzi nas ile.@Eval()zajmie się tym.

Następnie sprawdzamy, czy !na końcu łańcucha znajduje się znak . Jeśli istnieje, dołączamy 1do !ciągu ( 0!i 1!oba mają wartość 1 - nie ma znaczenia, ile !znaków jest na końcu), w przeciwnym razie dołączamy ostatni znak bez zmian, ponieważ nie jest to a, !a może być albo a 1albo 0.

Mamy teraz ciąg zawierający wiodące inwersje oraz liczbę zdefiniowaną przez to, czy są jakieś znaki silni, abyśmy mogli je nakarmić @Eval()i uzyskać wyniki powyżej.

ElPedro
źródło
2

sed, 36 33 31 bajtów

Czysty sed, bez narzędzi bc / shell. Działa na GNU sed <4.3; 33 bajty na BSD i GNU 4.3+.

s/.!!*$/1/
:
s/!0/1/
s/!1/0/
t

Dość proste, jeśli znasz sed; skomentował tych, którzy nie są:

# Since 0! == 1! == 1 and factorial has precedence, just collapse any trailing "!" 
s/.!!*$/1/
# Define an anonymous label
:
# Invert 0 if needed
s/!0/1/
# Invert 1 if needed
s/!1/0/
# If a change was made, go back to the anonymous label.
t

Test:

% cat 109248.sed
s/.!!*$/1/
:l
s/!0/1/
s/!1/0/
tl
% wc -c 109248.sed
      33 109248.sed
% cat cases
0
1
0!
1!
!0
!1
!0!
!1!
0!!
1!!
!!0
!!1
!0!!
!!!1
!!!0!!!!
!!!1!!!!
% sed -f 109248.sed cases
0
1
1
1
1
0
0
0
1
1
0
1
0
0
0
0
% gsed -f 109248.sed cases
0
1
1
1
1
0
0
0
1
1
0
1
0
0
0
0
%
Kevin
źródło
IIRC niektóre (wszystkie?) Wersje sedpozwalają na użycie łańcucha zerowego jako nazwy etykiety. Jeśli możesz to tutaj uruchomić, zaoszczędzi to dwa bajty. Właściwie nie jestem pewien, czy etykieta jest nawet potrzebna; chyba że coś przeoczyłem, pierwsza linia jest idempotentna, więc możesz być w stanie wrócić do początku programu zamiast potrzebować etykiety.
@ ais523 Też tak myślałem, ale najwyraźniej nie działa w wersjach BSD. Strona podręcznika mówi „Jeśli nie określono żadnej etykiety, przejdź do końca skryptu”, a nawet to nie działało, kiedy próbowałem.
Kevin
GNU sed zezwala na to, aby etykieta była po prostu :(bardziej jako błąd traktowany jako funkcja), w którym to przypadku zarówno ti b! polecenia skaczą do pozycji etykiety. Dodatkowo, kod sed musi działać dla co najmniej jednej wersji sed, podobnie jak w innych językach, więc nie musisz tworzyć kodu, który działa również dla BSD.
seshoumara
2

PHP 7.1, 58 55 54 37 35 bajtów

Uwaga: używa kodowania IBM-850

echo!!$argn[-1]^strspn($argn,~Ì)%2;

Uruchom tak:

echo '!!!0!!!!' | php -nR 'echo!!$argn[-1]^strspn($argn,~Ì)%2;';echo
> 0

Wyjaśnienie

echo
  strspn($a=$argv[1],~Ì) # Count the number of leading exclamation marks.
  % 2                    # Make 0 (even) or 1 (odd).
  ^ !!$a[-1];            # Negate with factorial part (truthy value of the 
                         # last char):
                         # - "0" is considered falsy.
                         # - "1" or "!" is considered truthy.

Poprawki

  • Zaoszczędzono 3 bajty przy użyciu kodowania IBM-850
  • Zapisano bajt, zmieniając nieznacznie regex
  • Zapisano 17 bajtów, nowa wersja bez długich nazw funkcji i powrotu
  • Zaoszczędzono 2 bajty -R(co $argnudostępnia)
aross
źródło
1

Fasola , 24 bajty

Hexdump:

00000000 26 4a c1 53 a0 17 53 d0 80 a0 5d 20 80 0a a1 80  &JÁS .SÐ. ] ..¡.
00000010 81 00 25 3a ae a1 ab 24                          ..%:®¡«$
00000018

Odpowiednik JavaScript:

+eval(a.replace(/.!+$/,1))

Przepraszam, że nadepnąłem ci na palce, Arnauld .

Wyjaśnienie:

Zajmuje pierwszą linię wejścia jako niesformatowany smyczkowy ai zastępuje dowolną cyfrę a następnie przez jeden lub więcej !z 1tak, że reszta może być eval„d przez JavaScript.

Wypróbuj wersję demonstracyjną lub pakiet testowy

Patrick Roberts
źródło