Prosty kalkulator operacji na liczbach całkowitych

28

Zaimplementuj prosty skryptowy kalkulator operacji na liczbach całkowitych.

Pojęcie

Akumulator zaczyna się od 0 i wykonuje na nim operacje. Na koniec programu wypisuje wartość akumulatora.

Operacje:

  • +dodaje 1do akumulatora
  • -odejmuje 1od akumulatora
  • * mnoży akumulator przez 2
  • / dzieli akumulator przez 2

Przykładowy skrypt

Dane wejściowe ++**--/powinny dawać dane wyjściowe 3.

Przykładowa implementacja

def calc(s)
    i = 0
    s.chars.each do |o|
        case o
            when '+'
                i += 1
            when '-'
                i -= 1
            when '*'
                i *= 2
            when '/'
                i /= 2
        end
    end
    return i
end

Zasady

  • To jest , więc najniższa odpowiedź w bajtach wygrywa, ale nie jest wybrana.
  • Zachęca się do kreatywnych wdrożeń.
  • Standardowe luki są zabronione.
  • Otrzymujesz program za pomocą stdin lub argumentów i możesz wyprowadzić odpowiedź za pomocą wartości zwracanej lub stdout.
  • Baw się dobrze.
  • Podział jest obcinany, ponieważ jest to podział na liczby całkowite.
  • Program -/powraca -1.

Przypadki testowe

*///*-*+-+
-1
/*+/*+++/*///*/+-+//*+-+-/----*-*-+++*+**+/*--///+*-/+//*//-+++--++/-**--/+--/*-/+*//*+-*-*/*+*+/+*-
-17 
+++-+--/-*/---++/-+*-//+/++-*--+*+/*/*/++--++-+//++--*/***-*+++--+-*//-*/+*/+-*++**+--*/*//-*--**-/-*+**-/*-**/*+*-*/--+/+/+//-+*/---///+**////-*//+-+-/+--/**///*+//+++/+*++**++//**+**+-*/+/*/*++-/+**+--+*++++/-*-/*+--/++*/-++/-**++++/-/+/--*/-/+---**//*///-//*+-*----+//--/-/+*/-+++-+*-*+*+-/-//*-//+/*-+//+/+/*-/-/+//+**/-****/-**-//+/+-+/*-+*++*/-/++*/-//*--+*--/-+-+/+/**/-***+/-/++-++*+*-+*+*-+-//+/-++*+/*//*-+/+*/-+/-/*/-/-+*+**/*//*+/+---+*+++*+/+-**/-+-/+*---/-*+/-++*//*/-+-*+--**/-////*/--/*--//-**/*++*+/*+/-+/--**/*-+*+/+-*+*+--*///+-++/+//+*/-+/**--//*/+++/*+*////+-*-//--*+/*/-+**/*//+*+-//+--+*-+/-**-*/+//*+---*+//*/+**/*--/--+/*-*+*++--*+//+*+-++--+-*-*-+--**+/+*-/+*+-/---+-*+-+-/++/+*///*/*-+-*//-+-++/++/*/-++/**--+-////-//+/*//+**/*+-+/+/+///*+*///*-/+/*/-//-*-**//-/-+--+/-*--+-++**++//*--/*++--*-/-///-+/+//--+*//-**-/*-*/+*/-*-*//--++*//-*/++//+/-++-+-*/*-+++**-/-*++++**+-+++-+-***-+//+-/**-+/*+****-*+++*/-*-/***/-/*+/*****++*+/-/-**-+-*-*-++**/*+-/*-+*++-/+/-++*-/*-****-*
18773342
dkudriavtsev
źródło
2
Więc ... nie jest ściśle liczbą całkowitą, ponieważ /może dawać liczby całkowite.
Conor O'Brien
2
Następnie powinieneś to wyraźnie określić.
Conor O'Brien
5
Co powinieneś -/zwrócić?
Dennis
4
Nie mogę nie zauważyć, że fragment kodu znajdujący się na stronie głównej rust-lang rozwiązuje to wyzwanie.
Zwei
4
Dodaj więcej przypadków testowych.
Martin Ender

Odpowiedzi:

28

Python 2, 48 bajtów

i=0
for c in input():exec"i=i%s2&-2"%c
print i/2

Czy +2, -2, *2, lub /2. Dzięki temu +2i -2zamiast +1a -1, pracujemy w podwójnych jednostek, więc ostateczne potrzeby wyjściowe o połowę. Poza tym podział podłogi /musi teraz zaokrąglić w dół do wielokrotności 2, co jest zrobione &-2.

xnor
źródło
To jest genialne! Jeśli chcesz opublikować to sam, port CJam byłby obecnie głównym wyzwaniem: 0q{2\~-2&}/2/( 2\~ewaluuje operator z drugim operandem 2, -2&jest bitowy AND, 2/jest końcowym podziałem na dwa. q{...}/Jest foreach nad wejściem i 0jest tylko początkowym wartość.)
Martin Ender
Możesz to opublikować, nie znam CJam.
xnor
Naprawdę sprytne! Przeniesiony do ES6 z łatwością przewyższy moją odpowiedź
edc65,
Świetne użycie pytona. Nauczyłem się z tego czegoś nowego.
Jacobr365,
12

Haskell, 51 bajtów

x#'+'=x+1
x#'-'=x-1
x#'*'=x*2
x#_=div x 2 
foldl(#)0

Przykład użycia: foldl(#)0 $ "++**--/"-> 3.

nimi
źródło
12

Galaretka , 18 17 bajtów

‘

’

:2
Ḥ
O0;ṛĿ/

Wypróbuj online!

Jak to działa

Pierwsze sześć linii definiuje linki pomocnicze o indeksach od 1 do 6 ; zwiększają, nic nie robią, zmniejszają, nic nie robią, zmniejszają o połowę (podłogi) i podwajają.

Główny link - O0;ṛĿ/- konwertuje znaki wejściowe na ich punkty kodowe ( O), wstawia wartość 0 (wartość początkowa) do tablicy punktów kodowych 0;, a następnie zmniejsza wygenerowaną tablicę w następujący sposób.

Wartość początkowa jest pierwszym elementem tablicy, tzn. Poprzedzonym 0 . Szybkie łącze ṛĿjest wywoływane dla każdego następnego elementu w tablicy, przy czym ostatnia zwracana wartość to lewy argument, a bieżący element - prawy. Sprawdza poprawny argument ( ) i monadycznie ocenia łącze z tym indeksem ( Ŀ), stosując w ten sposób żądaną operację.

Dennis
źródło
10
To wygląda jak galaretka odpowiedź z najbardziej nowymi wierszami
Conor O'Brien
10

Python 2, 54 bajty

i=0
for c in input():exec"i=i"+c+`~ord(c)%5%3`
print i

Dane wejściowe są traktowane jako literał łańcuchowy. ~ord(c)%5%3odwzorowuje operatorów na odpowiednie odpowiednie operandy.

Wcześniej korzystałem, hash(c)%55%3co nie dawało spójnych wyników między różnymi wersjami Pythona. Zachęciło mnie to do zbadania innych formuł.

xsot
źródło
wydaje się nie działać ...
Destructible Lemon
55,3 i 65,4 to dwa najkrótsze dla podwójnego modu mieszania w pythonie 2
Jonathan Allan
@DestructibleWatermelon robi dla mnie: ideone
Jonathan Allan
Myślę, że hashjest specyficzna dla wersji Python - ideone używa wersji 2.7.10, która daje [1, 1, 2, 2]cztery mapowania, podczas gdy lokalnie w wersji 2.7.12 otrzymuję[2, 0, 1, 0]
Sp3000,
1
działa na ideone, ale nie na moich komputerach python. Prawdopodobnie zależna od wersji, w którym to przypadku należy odnotować wersję EDYCJA: ninja'd: /
Destructible Lemon
10

SILOS , 133 211 bajtów

:s
def : lbl G GOTO
readIO
i-46
if i a
i+2
if i b
i+2
if i c
i+1
if i d
G e
:a
G v
:p
a-1
a/2
G o
:v
a+1
if a p
a-1
j=a
j/2
k=j
k*2
k-a
a/2
if k t
G o
:t
a-1
:o
G s
:b
a-1
G s
:c
a+1
G s
:d
a*2
G s
:e
printInt a

Pobiera kody ASCII operatorów.

Wypróbuj online z przypadkami testowymi:
-/
++**--/
*///*-*+-+

betseg
źródło
jest golfem loadLine?
Rohan Jhunjhunwala
PO wyjaśnił; -/powinien zwrócić -1 , a nie 0 .
Dennis
@Dennis naprawiony. Dodano wiele bajtów: /
betseg
9

Maszyna Turinga - 23 stany (684 bajty)

Wypróbuj tutaj - bezpośredni link

0 * * r 0
0 _ . l 1
1 * * l 1
1 _ * l 2
2 * 0 r 3
3 _ * r 3
3 + _ l +
3 - _ l -
3 x _ l x
3 / _ l /
+ _ * l +
+ * * * 4
4 - * l 5
4 _ 1 r 6
4 0 1 l 7
4 1 0 l 4
- _ * l -
- * * * 5
5 - * l 4
5 _ * r 8
5 0 1 l 5
5 1 0 l 7
x * * l x
x 1 0 l 9
x 0 0 l a
9 _ 1 r 6
9 1 1 l 9
9 0 1 l a
a _ _ r 6
a 1 0 l 9
a 0 0 l a
/ _ * l /
/ * * l b
b * * l b
b _ * r c
c 0 0 r d
c 1 0 r e
d * * l 7 
d 0 0 r d
d 1 0 r e
e _ * l 7
e - * l 4
e 0 1 r d
e 1 1 r e
8 * * r 8
8 - _ r 3
8 _ - r 3
7 * * l 7
7 _ * r f
f 0 _ r f
f 1 * r 6
f * _ l g
g * 0 r 6
6 * * r 6
6 _ * r 3
3 . _ l h
h _ * l h
h - _ l i
h * * l halt
i * * l i
i _ - r halt

Dane wejściowe nie powinny zawierać żadnego „*”, ponieważ jest to znak specjalny w kodzie maszynowym Turinga. Zamiast tego użyj „x”. Wysyła odpowiedź w formacie binarnym.

Kod nieobjawiony

init2 * * r init2
init2 _ . l init0
init0 * * l init0
init0 _ * l init1
init1 * 0 r readop
readop _ * r readop
readop + _ l +
readop - _ l -
readop x _ l x
readop / _ l /
+ _ * l +
+ * * * inc
inc - * l dec
inc _ 1 r return
inc 0 1 l zero
inc 1 0 l inc
- _ * l -
- * * * dec
dec - * l inc
dec _ * r neg
dec 0 1 l dec
dec 1 0 l zero
x * * l x
x 1 0 l x1
x 0 0 l x0
x1 _ 1 r return
x1 1 1 l x1
x1 0 1 l x0
x0 _ _ r return
x0 1 0 l x1
x0 0 0 l x0
/ _ * l /
/ * * l //
// * * l //
// _ * r div
div 0 0 r div0
div 1 0 r div1
div0 * * l zero 
div0 0 0 r div0
div0 1 0 r div1
div1 _ * l zero
div1 - * l inc
div1 0 1 r div0
div1 1 1 r div1
neg * * r neg
neg - _ r readop
neg _ - r readop
zero * * l zero
zero _ * r zero1
zero1 0 _ r zero1
zero1 1 * r return
zero1 * _ l zero2
zero2 * 0 r return
return * * r return
return _ * r readop
readop . _ l fin
fin _ * l fin
fin - _ l min
fin * * l halt
min * * l min
min _ - r halt

Objaśnienie stanów:

Inicjalizacja:
te stany są odwiedzane raz na początku każdego uruchomienia, zaczynając od init2

  • init2: Przesuń całkowicie w prawo i wpisz „.”. W ten sposób TM wie, kiedy przestać. Zmień na „init0”.
  • init0: Przesuń wszystkie plecy w lewo, aż głowa przeczyta spację. Następnie przesuń jedną komórkę w lewo. Zmień na „init1”.
  • init1: Ustaw zero i przesuń jedną komórkę w prawo i zmień na „readop”.

Instrukcje czytania:
te stany będą odwiedzane wiele razy w całym programie

  • readop: Przechodzi do końca w prawo, dopóki nie odczyta operatora lub „.”. Jeśli uderza operator, zmień na odpowiedni stan (+, -, x, /). Jeśli trafi w „.”, Zmień na „płetwa”.

  • return: Zwraca głowę do pustej przestrzeni między sumą bieżącą a operatorami. Następnie zmienia się na „readop”.

Operacje:
te operacje wykonują faktycznie brudną robotę

  • +: Poruszaj się w lewo, dopóki głowa nie odczyta żadnego spacji. Jeśli ta postać to „-”, przesuń się w lewo i zmień na „dec”. W przeciwnym razie zmień na „inc”.

  • -: Podobne do „+”, z wyjątkiem zmiany na „inc”, jeśli w przeciwnym razie występuje „-” i „dec”.

  • inc: Jeśli cyfra pod głową to 0 (lub biała spacja), zmień ją na 1 i zmień na „zero”. Jeśli cyfra to 1, zmień ją na 0, a następnie powtórz na następnej cyfrze.

  • dec: Podobnie jak inc, z tym wyjątkiem, że 1 idzie do 0, 0 idzie do 1, a jeśli głowa czyta biały znak, zmień na „neg”.

  • x, x0, x1: Przesunięcie bitowe cyfry jeden w lewo. Zmień na „return”.

  • /, //, div, div0, div1: Przesuń całkowicie na prawo od liczby, a następnie przesuń bitowo jeden w prawo. Jeśli występuje „-”, zmień na „inc”. To symuluje zaokrąglanie w dół liczb ujemnych. W przeciwnym razie zmień na „zero”

  • neg: umieść „-” po numerze, a następnie zmień na „readop”

  • zero, zero1, zero2: Usuń wiodące zera i zmień na „readop”

Oczyszczanie: Prezentuje dane wyjściowe

  • fin, min: W razie potrzeby przesuń „-” przed liczbą. Postój.
KoreanwGlasses
źródło
1
Myślałem, że czytanie tego kodu było bardzo, bardzo fajne. Dziękuję za rozjaśnienie mojego dnia.
Jacobr365,
8

Perl 6 , 53  52 bajty

{([Ro] %(<+ - * />Z=>*+1,*-1,* *2,*div 2){.comb})(0)}

{[Ro](%(<+ - * />Z=>*+1,*-1,*×2,*div 2){.comb})(0)}

Wyjaśnienie:

# bare block lambda that has one implicit parameter 「$_」
{
  (
    # reduce the code refs using ring operator 「∘」 in reverse 「R」
    [R[o]]

      # produce a hash from:
      %(

        # list of pairs of "operator" to code ref
        # ( similar to 「'+' => { $^a + 1 }」 )

          # keys
          < + - * / >

        # keys and values joined using infix zip operator 「Z」
        # combined with the infix Pair constructor operator 「=>」
        Z[=>]

          # values (Whatever lambdas)
          * + 1,
          * - 1,
          * × 2, # same as 「* * 2」
          * div 2,

      ){

        # split the block's argument into chars
        # and use them as keys to the hash
        # which will result in a list of code refs
        .comb

      }

  # call composed code ref with 0
  )(0)
}

Stosowanie:

my $input = '++**--/'
my $output = {[Ro](%(<+ - * />Z=>*+1,*-1,*×2,*div 2){.comb})(0)}.( $input );
say $output; # 3
say $output.^name; # Int
Brad Gilbert b2gills
źródło
7

C, 63 62 57 bajtów

s,t;c(char*x){for(;*x;s+=t<4?t?2-t:s:-s>>1)t=*x++%6;s=s;}

Wandbox

o79y
źródło
6

05AB1E , 20 bajtów

Dzięki Enigma za naprawienie -/błędu!

Do 16 bajtów, jeśli nie całkowita podziału: Î"+-*/""><·;"‡.V.

Î…+-*"><·"‡'/"2÷":.V

Wyjaśnienie:

Î                      # Push 0, which is our starting variable, and input
 …+-*                  # Push the string "+-*"
     "><·"             # Push the string "><·"
          ‡            # Transliterate. The following changes:
                           "+" -> ">"
                           "-" -> "<"
                           "*" -> "·"
           '/"2÷":     # Replace "/" by "2÷"
                  .V   # Evaluate the code as 05AB1E code...
                           '>' is increment by 1
                           '<' is decrement by 1
                           '·' is multiply by 2
                           '2÷' is integer divide by two
                       # Implicitly output the result

Wykorzystuje kodowanie CP-1252 . Wypróbuj online!

Adnan
źródło
PO wyjaśnił; -/powinien zwrócić -1 , a nie 0 .
Dennis
Problem z dzieleniem liczb ujemnych można rozwiązać Î…+-*"><·"‡'/"2÷":.Vza pomocą tej samej liczby bajtów.
Emigna
@Dennis Naprawiono problem.
Adnan
@Emigna Thanks :)
Adnan
5

JavaScript ES6, 80 68 bajtów

k=>[...k].reduce((c,o)=>+{"+":c+1,"-":c-1,"*":c*2,"/":c/2|0}‌​[o],0)

Zaoszczędził aż 12 bajtów dzięki Neilowi!

Conor O'Brien
źródło
Druga odpowiedź byłaby bardziej czytelna, gdybyś usunął "c"+i napisał "c+1 c-1 c*2 c/2|0".splititp.
Neil
Na pierwszą odpowiedź, dlaczego nie napisać o=>c=[c+1,c-1,c*2,c/2|0]["+-*/".indexOf(o)], lub myślę, że możesz następnie zapisać kolejny bajt za pomocą o=>c={"+":c+1,"-":c-1,"*":c*2,"/":c/2|0}[o].
Neil
k=>[...k].reduce((c,o)=>+{"+":c+1,"-":c-1,"*":c*2,"/":c/2|0}[o],0)może i tak będzie działać jeszcze krócej, ale straciłem rachubę ...
Neil
@Neil Ah, tak, zapomniałem o tym
Conor O'Brien
1
Jakoś dostałeś znaki o zerowej szerokości pomiędzy }i [o], więc w rzeczywistości ma on tylko 66 bajtów. Ponadto wyjaśniono PO; -/powinien zwrócić -1 , a nie 0 .
Dennis
5

Rubinowy, 48 44 42 + 1 = 43 bajty

+1 bajt dla -nflagi. Pobiera dane wejściowe na STDIN.

i=0
gsub(/./){i=i.send$&,"+-"[$&]?1:2}
p i

Zobacz to na ideone (używa, $_ponieważ ideone nie przyjmuje flag wiersza poleceń): http://ideone.com/3udQ3H

Jordania
źródło
5

PHP 76 bajtów

for(;$c=$argv[1][$n++];)eval('$s=floor($s'.$c.(2-ord($c)%11%3).');');echo$s;
Jörg Hülsermann
źródło
4

Python 2, 58 56 bajtów

-2 bajty dzięki @Lynn

r=0
for c in input():exec'r=r'+c+`2-ord(c)%11%3`
print r

W porządkowe bohaterów +-*/43,45,42,47modulo 11 są 10,1,9,3modulo 3 to są 1,1,0,02 mniej te są 1,1,2,2dając kwot musimy dla każdej operacji: r=r+1, r=r-1, r=r*2, ir=r/2


Poprzedni:

r=0
for c in input():exec'r=r'+c+`(ord(c)%5==2)+1`
print r
Jonathan Allan
źródło
Jak o 2-ord(c)%11%3?
Lynn
@ Lynn Cóż, wezmę to, jeśli jest w porządku z tobą? (ale naprawdę myślę, że to wystarczy, byś mógł to opublikować)
Jonathan Allan
2
Śmiało :) ----
Lynn,
4

Mathematica, 83 73 70 bajtów

10 bajtów zapisanych z powodu @MartinEnder .

(#/*##2&@@#/.Thread[{"+","-","*","/"}->{#+1&,#-1&,2#&,⌊#/2⌋&}])@0&

Funkcja anonimowa. Pobiera listę znaków jako dane wejściowe i zwraca liczbę jako dane wyjściowe. Sugestie dotyczące gry w golfa mile widziane.

LegionMammal978
źródło
4

SILOS , 175 164 bajtów

loadLine
a=256
o=get a
lbla
a+1
o-42
p=o
p-1
p/p
p-1
r-p
s=o
s-3
s/s
s-1
r+s
m=o
m/m
m-2
m|
r*m
t=r
t%2
d=o
d-5
d/d
d-1
t*d
d-1
d|
r-t
r/d
o=get a
if o a
printInt r

Wypróbuj online!

Zdrowa metoda wprowadzania. Prawidłowy podział na liczby całkowite (zaokrąglenie w kierunku-nieskończoności).

Leaky Nun
źródło
4

C #, 87 81 bajtów

int f(string s){int i=0;foreach(var c in s)i=c<43?i*2:c<46?i+44-c:i>>1;return i;}

Nie golfowany:

int f(string s)
{
    int i = 0;

    foreach (var c in s)
        i = c < 43 ? i * 2
          : c < 46 ? i + 44 - c
          : i >> 1;

    return i;
}

Zakłada się, że dane wejściowe są prawidłowe. Dzielenie przez dwa odbywa się poprzez przesunięcie jednego bitu w prawo, ponieważ regularne dzielenie zawsze zaokrągla w kierunku zera, a przesunięcie bitu zawsze zaokrągla w dół. Inkrementacja i dekrementacja umożliwiają wygodne wykorzystanie 1 odległości między kodami ASCII dla +i -.

Scepheo
źródło
Trochę miłości do nowej składni C # 6 i metody agregacji Linq? int f(string s)=>s.Aggregate(0,(i,c)=>c<43?i*2:c<46?i+44-c:i>>1);(65 bajtów)
Cyril Gandon
@CyrilGandon, o ile mi wiadomo, że musiałoby zawierać „using System.Linq;”, co wydłużyłoby go o 19 i oznaczało 84 bajtów. Dlatego tego nie zrobiłem.
Scepheo,
4

JavaScript (ES6), 57 bajtów (tablica) / 60 bajtów (liczba całkowita)

Zwracanie tablicy wszystkich wyników pośrednich:

o=>[...o].map(c=>x=[x>>1,x+1,x*2,x-1][eval(2+c+3)&3],x=0)

Na przykład wynikiem "++**--/"będzie [1, 2, 4, 8, 7, 6, 3].

Zwracanie tylko wyniku końcowego:

o=>[...o].reduce((x,c)=>[x>>1,x+1,x*2,x-1][eval(2+c+3)&3],0)

Jak to działa

Oba rozwiązania są oparte na tej samej idei: za pomocą funkcji skrótu idealny eval(2+c+3)&3do mapowania różnych znaków operatora cw [0, 3].

 operator | eval(2+c+3)  | eval(2+c+3)&3
----------+--------------+---------------
    +     |  2+3 = 5     |    5 & 3 = 1
    -     |  2-3 = -1    |   -1 & 3 = 3
    *     |  2*3 = 6     |    6 & 3 = 2
    /     |  2/3 ~= 0.67 | 0.67 & 3 = 0
Arnauld
źródło
3

JavaScript (ES6), 57

a=>[...a].map(c=>a=c<'+'?a<<1:c<'-'?-~a:c<'/'?~-a:a>>1)|a

Uwaga: wartość początkowa akumulatora jest ciągiem programu, przy użyciu operacji bitowych (~, >>, <<, |) przy pierwszym użyciu jest przekształcana na 0.

Na marginesie, sprytna odpowiedź @xnor uzyska 40 punktów przeniesionych do javascript:

a=>[...a].map(c=>a=eval(~~a+c+2))&&a>>1

(jeśli ci się spodoba, głosuj na niego)

Test

f=a=>[...a].map(c=>a=c<'+'?a<<1:c<'-'?-~a:c<'/'?~-a:a>>1)|a

function update() {
  O.textContent = f(I.value);
}

update()
<input value='++**--/' id=I oninput='update()'><pre id=O></pre>

edc65
źródło
3

Java, 77 bajtów

int f(String s){return s.chars().reduce(0,(r,c)->c<43?r*2:c<46?r+44-c:r>>1);}

Korzysta z 8 strumieni Java.

pierwiosnek
źródło
1
Ładna odpowiedź i witamy na stronie! Nie wiem nic na temat java wiem, ale można zmienić r >> 1na r>>1zaoszczędzisz 2 bajty?
DJMcMayhem
Masz absolutną rację, dziękuję @DJMcMayhem
primodemus
1
Wspaniale, cieszę się, że mogłem pomóc! Jeszcze jedna uwaga, liczę 77 bajtów. Czy zdarzyło Ci się dołączyć nowy wiersz do liczby bajtów? Możesz usunąć jeszcze jeden bajt, ponieważ nie jest to konieczne.
DJMcMayhem
Popraw ponownie @DJMcMayhem, najwidoczniej wc liczy bajt kończący zerem lub coś w tym stylu ...
Primodemus 30.08.16
1
jak używasz java8, dlaczego nie zdefiniuj funkcji za pomocą lambda, s->s.chars().reduce(0,(r,c)->c<43?r*2:c<46?r+44-c:r>>1);która da ci 56 bajtów
user902383
3

GNU sed, 65 59 57 bajtów

Edycja: 2 bajty krótsze dzięki komentarzom Toby'ego Speighta

s/[+-]/1&/g
s/*/2&/g
s:/:d0>@2&:g
s/.*/dc -e"0[1-]s@&p"/e

Biegać:

sed -f simple_calculator.sed <<< "*///*-*+-+"

Wydajność:

-1

sedScenariusz przygotowuje wejście dla dcwywołania powłoki na koniec, ten ostatni przyjmując wejście w notacji polskiej tyłu . Przy dzieleniu, jeśli liczba jest ujemna ( d0>), wywoływane jest [1-]polecenie zmniejszenia zapisane w rejestrze @. Przykład konwersji: + - * /-> 1+ 1- 2* d0>@2/.

seshoumara
źródło
Nie potrzebujesz cudzysłowów wokół argumentu do dc, jeśli nie ma spacji i plików pasujących do [1-]wzorca ...
Toby Speight
@TobySpeight W mojej głowie zmieniłem znaczenie sz S. Zapomniałem, że to nie zastępuje stosu rejestru, tylko na niego naciska, wywołując efekt przeciwny do tego, czego chciałem (ponieważ używałem go do każdego /). Cytaty są nadal potrzebne, ponieważ masz w nich /symbole, dzięki czemu ciąg interpretowany jest jako ścieżka do pliku :) Ogoliłem jeszcze 1 bajt, usuwając spację po -e.
seshoumara,
1
dc nie zinterpretuje argumentu -ejako nazwy pliku, więc nie potrzebujesz cudzysłowów /- spróbuj! Myślę, że rozsądne jest, aby golfista wymagał, aby bieżący katalog roboczy nie zawierał żadnych plików zaczynających się od 01s@lub 0-s@.
Toby Speight
@TobySpeight miałeś rację co -edo tego /, jednak cytaty są nadal wymagane, jak właśnie zobaczyłem. >Jest interpretowana bezpośrednio przez powłokę jako operator przekierowania myślę, bo mam ten błąd:cannot create @2/d0: Directory nonexistent
seshoumara
Ach, tak, nie brałem pod uwagę >. W końcu potrzebujesz cytatów. Przepraszamy za próbę wprowadzenia w błąd! I chociaż dodanie odwrotnego ukośnika wygląda jak jedna postać, należy go podwoić w s///zastępstwie, więc nie ma żadnej korzyści ...
Toby Speight
3

PHP, 75 bajtów

Wykorzystuje zmodyfikowaną wersję odpowiedzi Jörga Hülsermanna .

eval(preg_replace('~.~','$s=($s\0(2-ord("\0")%11%3))|0;',$argv[1]));echo$s;

W dużej mierze opiera się na podstawianiu ciągów znaków, używając prostego wyrażenia regularnego ( ~.~).

Zmienna $sjest ponownie przypisywana z nową wartością dla każdego znaku. Na koniec wyprowadza wynik.


Uwaga : To ma być wykonane przy użyciu -rflagi.


Wypróbuj tutaj:

Lub spróbuj na: http://sandbox.onlinephpfunctions.com/code/7d2adc2a500268c011222d8d953d9b837f2312aa

Różnice:

  • Zamiast tego echo$sużywam sprintf($s). Oba wykonują tę samą akcję na liczbach. Ponieważ jest to tylko do testowania, jest w porządku.
  • W przypadku braku przekazanego argumentu będzie on działał tak, jakbyś podał ++*+jako pierwszy argument, który powinien zostać wyświetlony 5.
Ismael Miguel
źródło
Tak! eModyfikator jest z powrotem! : D
Tytus
@Titus Nie rozumiem. Czy możesz trochę rozwinąć?
Ismael Miguel
PHP przed wersją 7 miał modyfikator wzorcae , który został zastąpiony przez preg_replace_callbacki może być wykorzystany do ... ale to nie do końca.
Tytus
@Titus Ten modyfikator patern został użyty, aby powiedzieć, że wyjście będzie rzeczywistym kodem PHP, i spróbować zachować poprawną składnię. To tutaj nie używa go, ale zastępuje każdy znak kawałkiem kodu do wykonania, niezależnie od jego składni. Złe dane wejściowe spowodują poważne problemy z bezpieczeństwem.
Ismael Miguel
Wiem. Ale to przypomina.
Tytus
2

Partia, 61 bajtów

@set n=
@for %%a in (%*)do @set/an=n%%a2^&-2
@cmd/cset/an/2

Tłumaczenie znakomitej odpowiedzi Python na xnor.

Neil
źródło
2

Pyke, 24 22 bajtów

\*\}:\/\e:\+\h:\-\t:0E

Wypróbuj tutaj!

Lub 12 bajtów (niekonkurencyjny)

~:"ht}e".:0E

Wypróbuj tutaj!

Dodaj translatewęzeł - w zasadzie wiele znajdź i zamień.

~:           -   "+-*/"
        .:   -  input.translate(^, V)
  "ht}e"     -   "ht}e"
          0E - eval(^, stack=0)
niebieski
źródło
2

PHP, 104 102 82 bajtów

Pierwsza wersja z eval:

$i=0;while($c<9999)eval('$i'.['+'=>'++','-'=>'--','*'=>'*=2','/'=>'>>=1'][$argv[1]{$c++}].';');echo$i;

Druga wersja z operatorami trójskładnikowymi:

while($o=ord($argv[1]{$c++}))$i=$o<43?$i*2:($o<44?$i+1:($o<46?$i-1:$i>>1));echo$i;

Bierze ciąg wejściowy jako pierwszy argument z wiersza poleceń.

To „tylko” działa na ciągi wejściowe krótsze niż 10 000 znaków - co powinno być wystarczające. Testowane ze wszystkimi przypadkami testowymi, niestety nie można początkowo zaoszczędzić na inicjalizacji. Druga wersja działa z ciągami o dowolnej długości i bez inicjalizacji. :-)

Głównym elementem jest funkcja eval, która manipuluje $ina podstawie mapy operacji arytmetycznych, które są dość proste, z wyjątkiem podziału. PHP zwraca liczbę zmiennoprzecinkową podczas używania /i intdivma za dużo bajtów, więc wykonujemy przesunięcie w prawo .

Aktualizacje

  1. Zaoszczędzono 2 bajty, skracając $i=$i>>1do $i>>=1podziału liczb całkowitych.
  2. Wyrzucił eval na korzyść operatorów trójskładnikowych.
YetiCGN
źródło
2

Python 3, 98 66 60 bajtów

Dzięki Tukkax!

Nie tak golfowa jak druga odpowiedź, ale nie mogę z nimi konkurować bez plagiatu.

i=0
for c in input():i+=[1,-i//2,-1,i][ord(c)%23%4]
print(i)

Mam też rekurencyjne rozwiązanie lambda

73 67 bajtów (ulepszone!)

s=lambda x,z=0:s(x[1:],z+[1,-z//2,-1,z][ord(x[0])%23%4])if x else z
Zniszczalna cytryna
źródło
Dzięki zastosowaniu część swojego rozwiązania rekurencyjnej wersji procesowego: 60 bajtów: i=0 for c in input():i+=[1,-i//2,-1,i][ord(c)%23%4] print(i). (oczywiście niepoprawnie sformatowane). Myślę też, że powinieneś wspomnieć, że używasz Python3. W Python2 input()miałby wartość int(raw_input()).
Yytsi
@TuukkaX nie działa dla z = 0 ( +-robi 1)
Destructible Lemon
o tak, mój błąd.
Yytsi
1
Dodaj tytuł Python3, proszę.
Yytsi
2

R, 201 bajtów

Grał w golfa

p=.Primitive;"-"="+"=function(x)p("+")(x,1);body(`-`)[[1]]=p("-");"*"="/"=function(x)p("*")(x,2);body(`/`)[[1]]=p("%/%");Reduce(function(f, ...)f(...),rev(mget(strsplit(scan(stdin(),""),"")[[1]])),0,T)

Skomentował

p = .Primitive                       # Redefine
"-" = "+" = function(x)p("+")(x,1)   # Define - and +
body(`-`)[[1]] = p("-")              # Change the body, what we do to save a byte
"*" = "/" = function(x)p("*")(x,2)   # Same as above
body(`/`)[[1]] = p("%/%")            # Same as above
Reduce(function(f, ...)f(...),       # Function wrapper to evaluate list of func.  
  rev(mget(strsplit(scan(stdin(),""),"")[[1]])), # Strsplit input into list of functions
  init = 0,                                      # Starting Arg = 1
  right = T)                                     # Right to left = True 

Strategia polega na dopracowaniu +, -, %operatorów. Podziel ciąg, a następnie przeanalizuj go na długą listę funkcji, które zostaną wprowadzone do Reduce()'sakumulatora.

Nie mogłem już grać w golfa. Jeśli ktoś może zabrać się b=body<-do pracy, może być kilka bajtów oszczędności (dopracuj każdą funkcję bpóźniej "-"="+"="/"="*"). Początkowo próbował zastąpić i przeanalizować ewaluację, ale kolejność operacji i nawiasy były przerażające.

Vlo
źródło
Jest to rok później, ale udało mi się go 10 bajtów poprzez zamianę Twoje podejście trochę - można upuścić 8 bajtów usuwając przestrzeń pomiędzy f, ...w definicji Reducefunkcji i pozbycie stdin()się scan, ale po prostu starał naiwny podejście, które zrzuciło jeszcze dwa bajty, definiując funkcje nieco inaczej. tio.run/##XcvLCsMgEAXQrwnO6Gge29B/…
Giuseppe
1

Lex + C, 78 , 74 , 73 bajty

Pierwsza postać to spacja.

 c;F(){yylex(c=0);return c;}
%%
\+ c++;
- c--;
\* c*=2;
\/ c=floor(c/2.);

Odczytuje z stdin, zwraca wynik.

Kompiluj z lex golfed.l && cc lex.yy.c main.c -lm -lfltestowym głównym:

int main() { printf("%d\n", F()); }
Stefano Sanfilippo
źródło
1

JavaScript (ES5), 127 bajtów

function(b){for(a=c=0;a<b.length;++a)switch(b[a]){case"+":++c;break;case"-":--c;break;case"*":c*=2;break;case"/":c/=2}return c}

Nie golfowany:

function c(a){
  c=0;
  for(var i=0;i<a.length;++i){
    switch(a[i]){
      case "+":++c;break;
      case "-":--c;break;
      case "*":c*=2;break;
      case "/":c/=2;break;
    }
  }
  return c;
}
Paul Schmitz
źródło
1

Pyth, 23 bajty

FNQ=Z.v%".&%sZ2_2"N;/Z2

Pełny program, który pobiera dane wejściowe jako ciąg i wypisuje wynik.

To jest port odpowiedzi Python @ xnor .

Wypróbuj online

Jak to działa

FNQ=Z.v%".&%sZ2_2"N;/Z2   Program. Input: Q. Z initialised as 0
FNQ                       For. For N in Q:
        ".&%sZ2_2"         String. Literal string ".&%sZ2_2"
       %          N        String format. Replace %s with the current operator N
           %sZ2            Operator. Yield Z*2, Z//2, Z+2, Z-2 as appropriate
         .&    _2          Bitwise and. Result of above & -2
     .v                    Evaluate. Yield the result of the expression
   =Z                      Assignment. Assign result of above to Z
                   ;      End. End for loop
                    /Z2   Integer division. Yield Z//2
                          Print. Print the above implicitly 
TheBikingViking
źródło
1
Konwersja Pythona na Pyth jest przeważnie złym pomysłem. u@[yGhG0tG0/G2)CHQ019 bajtów
Jakube
@Jakube Dzięki - Jestem zupełnie nowy w Pyth, więc każda rada jest doceniana. Możesz to opublikować jako osobną odpowiedź, ponieważ jest to inne podejście.
TheBikingViking
1

PHP, 79 bajtów

<?$i=0;switch($_POST['a']){case"+":$i+1;case"-":$i-1;case"/":$i/2;case"*":$i*2}
Kubuś Puchatek
źródło
2
Uwzględnij liczbę bajtów w nagłówku, usuń niepotrzebne spacje i użyj 1-literowych nazw zmiennych.
TuxCrafting,
Czy to jest nawet gra w golfa ?! :-D
YetiCGN
@ TùxCräftîñg Zrobiłem to.
Kubuś Puchatek,
Dzielisz i mnożysz 1; musisz podzielić i pomnożyć przez2
TuxCrafting
@ TùxCräftîñg Zrobiłem to.
Kubuś Puchatek,