Yah itu aneh ... tidak tunggu, itu bahkan!

70

Pembukaan

Bilangan bulat selalu genap atau ganjil . Bahkan bilangan bulat dapat dibagi dua, bilangan bulat ganjil tidak.

Saat Anda menambahkan dua bilangan bulat, Anda dapat menyimpulkan apakah hasilnya akan genap atau ganjil berdasarkan apakah puncaknya genap atau ganjil:

  • Even + Even = Even
  • Genap + Ganjil = Ganjil
  • Ganjil + Genap = Ganjil
  • Ganjil + Ganjil = Merata

Demikian juga, ketika Anda mengalikan dua bilangan bulat Anda dapat menyimpulkan apakah hasilnya akan genap atau ganjil berdasarkan apakah faktor genap atau ganjil:

  • Even * Even = Even
  • Even * Odd = Even
  • Ganjil * Genap = Genap
  • Ganjil * Ganjil = Ganjil

Dengan demikian, jika Anda mengetahui kerataan atau keanehan semua variabel dalam ekspresi matematika yang hanya melibatkan penambahan dan perkalian, Anda dapat menyimpulkan apakah hasilnya akan genap atau ganjil.

Sebagai contoh, kita dapat dengan yakin mengatakan bahwa (68 + 99) * 37menghasilkan ganjil karena genap ditambah ganjil ( 68 + 99) adalah ganjil, dan yang ganjil lain ganjil ( odd * 37) memberikan ganjil.

Tantangan

Tulis program atau fungsi yang menggunakan string yang hanya berisi empat karakter eo+*. String ini mewakili ekspresi matematika yang diberikan dalam notasi awalan yang hanya melibatkan penambahan ( +) dan perkalian ( *). Masing-masing emewakili beberapa nomor genap sembarang, dan masing-masing omewakili beberapa angka ganjil yang sewenang-wenang.

Tugas Anda adalah menyederhanakan ekspresi, mencetak, atau mengembalikan tunggal eatau oberdasarkan apakah hasil ekspresi itu genap atau ganjil.

Anda dapat mengasumsikan bahwa input akan selalu dalam notasi awalan yang valid. Secara khusus, masing +- masing dan *akan selalu memiliki dua operan yang sesuai terjadi setelahnya. Operan ini dapat berupa satu eatau o, +atau *ekspresi lain yang pada gilirannya memiliki operan.

Misalnya, input *+eoodapat dibaca sebagai mul(add(e, o), o), atau (e + o) * odalam notasi infiks normal . The edan yang pertama oadalah operan sesuai dengan +, dan +eodan yang terakhir oadalah operan yang sesuai dengan *.

Untuk memperjelasnya, berikut adalah beberapa input yang tidak valid yang memiliki notasi awalan yang salah:

eo
ooe
o+e
ee*
+*oe
+e*o

Satu baris baru yang tertinggal di output baik-baik saja, tetapi jika tidak, plain euntuk genap atau oganjil adalah yang seharusnya menjadi output.

Kode terpendek dalam byte menang.

Uji Kasus

(Baris kosong hanya untuk membantu memisahkan kasus serupa secara visual.)

e -> e
o -> o

+ee -> e
+eo -> o
+oe -> o
+oo -> e
*ee -> e
*eo -> e
*oe -> e
*oo -> o

+e+ee -> e
+e+eo -> o
+e+oe -> o
+e+oo -> e
+e*ee -> e
+e*eo -> e
+e*oe -> e
+e*oo -> o

+o+ee -> o
+o+eo -> e
+o+oe -> e
+o+oo -> o
+o*ee -> o
+o*eo -> o
+o*oe -> o
+o*oo -> e

*e+ee -> e
*e+eo -> e
*e+oe -> e
*e+oo -> e
*e*ee -> e
*e*eo -> e
*e*oe -> e
*e*oo -> e

*o+ee -> e
*o+eo -> o
*o+oe -> o
*o+oo -> e
*o*ee -> e
*o*eo -> e
*o*oe -> e
*o*oo -> o

++eee -> e
++eeo -> o
++eoe -> o
++eoo -> e
++oee -> o
++oeo -> e
++ooe -> e
++ooo -> o

+*eee -> e
+*eeo -> o
+*eoe -> e
+*eoo -> o
+*oee -> e
+*oeo -> o
+*ooe -> o
+*ooo -> e

*+eee -> e
*+eeo -> e
*+eoe -> e
*+eoo -> o
*+oee -> e
*+oeo -> o
*+ooe -> e
*+ooo -> e

**eee -> e
**eeo -> e
**eoe -> e
**eoo -> e
**oee -> e
**oeo -> e
**ooe -> e
**ooo -> o

+e+e+e+ee -> e
+o+o+o+oo -> o
*e*e*e*ee -> e
*o*o*o*oo -> o
+e+o+e+oe -> e
+o+e+o+eo -> o
*e*o*e*oe -> e
*o*e*o*eo -> e
+e*e+e*ee -> e
+o*o+o*oo -> o
*e+e*e+ee -> e
*o+o*o+oo -> o

+**++*+*eeoeeooee -> e
+**++*+***eooeoeooeoe -> e
+**+***+**++**+eooeoeeoeeoeooeo -> o

+e*o*e**eoe -> e
+*e+e+o+e**eeoe -> e
**o++*ee*++eoe*eo+eoo -> o
Hobi Calvin
sumber
8
Bisakah kita mengambil 1 dan 0 bukannya e dan o sebagai input?
ghosts_in_the_code
8
@ghosts_in_the_code Tidak, maaf.
Hobi Calvin
2
Apakah menggunakan evalOK?
xnor
1
@xnor Tentu. Apapun yang berhasil.
Hobi Calvin
2
Saya ragu saya bisa menggunakan ini untuk mengalahkan 13 byte yang sudah diposting, tetapi saya perhatikan bahwa penambahan cocok dengan eksklusif atau dan perkalian yang sederhana atau.
WGroleau

Jawaban:

43

CJam, 18 17 13 byte

Terima kasih kepada aditsu karena telah menghemat 4 byte.

qW:O%eu~"eo"=

Coba test suite di sini. (Test suite terlalu panjang untuk permalink. Cukup salin dari spec tantangan.)

Penjelasan

q     e# Read the input.
W:O   e# Push a -1 and store it in variable O.
%     e# Use the -1 to reverse the string, because CJam's stack-based nature and the
      e# commutativity of the operators means we can evaluate the code in postfix notation.
eu    e# Convert the string to upper case, turning 'e' into 'E' (a variable with even value
      e# 14) and 'o' into 'O' (which we've stored the odd value -1 in).
~     e# Evaluate the string as CJam code, leaving the result on the stack.
"eo"= e# Use the result as an index into the string "eo". CJam's indexing is cyclic so it
      e# automatically takes inputs modulo 2. Negative indices also work as expected.
Martin Ender
sumber
27

Pyth, 16 14 byte

@"eo".vjdXzGU9

Pyth sendiri dapat mengevaluasi string, yaitu dalam sintaks Pyth. Karena itu saya ganti edan odengan 4dan 5. Maka evaluasi akan memberi saya nomor genap atau ganjil, dan saya dapat dengan mudah mencetak hasilnya.

Cobalah online: Demonstrasi atau Test Suite

Penjelasan:

@"eo".vjdXzGU9   implicit: z = input string
         XzGU9   replace "e" in z with 4 and "o" with 5
       jd        put a space between each char
     .v          evaluate it (Pyth style)
@"eo"            and print "e" or "o"

Penjelasan tambahan untuk mengganti. Gadalah variabel yang diinisialisasi dengan alfabet abc...xyz. U9adalah daftar [0, 1, ..., 8]. XzGU9mengganti huruf-huruf alfabet dengan nilai-nilai daftar. Jadi aakan diganti dengan 0, bdengan 1, ..., edengan 4, ..., idengan 8, jdengan 0, ..., dan odengan 5. Karena itu saya ediganti dengan angka genap dan oangka ganjil. Semua penggantian lainnya tidak berpengaruh sama sekali.

Jakube
sumber
Mengapa Anda membalikkan ekspresi? Juga, bukankah Anda perlu mengambil hasil modulo 2, atau apakah pengindeksan membungkus?
xnor
@ xnatau mengakses elemen dalam sebuah string dilakukan pembungkus modulo. Jadi tidak perlu untuk modulo 2.
Jakube
@ xnor Tapi terima kasih untuk hal sebaliknya. Tentu ini tidak perlu. (Aku agak lelah hari ini.)
Jakube
16

Perl, 50 45 40 karakter

(39 karakter kode + 1 opsi baris perintah karakter.)

1while s/\+oe|\+eo|\*oo/o/||s/\W\w\w/e/

Contoh dijalankan:

bash-4.3$ echo -n '**o++*ee*++eoe*eo+eoo' | perl -pe '1while s/\+oe|\+eo|\*oo/o/||s/\W\w\w/e/'
o
manatwork
sumber
Bagaimana dengan while/../?
primo
Doh. Saya bodoh. Sebenarnya menggunakan kondisi itu saat mencoba sedversinya ... Terima kasih, @primo.
manatwork
Atau lebih baik lagi 1while s/\+oe...,. Saya juga cukup yakin [+*]bisa diganti dengan \W.
primo
Sekali lagi terima kasih @primo. Saya pikir saya harus berkonsentrasi pada solusi tunggal sekali. ( gemaMembuatku gila ...)
manatwork
Pendekatan yang sama dengan Sed sekarang 2 byte lebih pendek!
Trauma Digital
13

Retina , 29 byte

(+`\*oo|\+(eo|oe)
o
\W\w\w
e

Untuk versi file satu nyaman -sbendera digunakan.

Kami bertukar ekspresi aneh ( *oo, +oe, +eo) untuk osampai kita bisa, maka menukar ekspresi simbol huruf-huruf yang tersisa untuk e. Kami ulangi ini sampai kami bisa dan huruf terakhir adalah hasil kami.

(Solusi ini mirip dengan jawaban Perl manatwork .)

Cobalah online! (oleh Dennis)

randomra
sumber
12

Python 2, 90

def f(s):i=iter(s);a=next(i);return(a>'a')*a or'oe'[f(i)==f(i)if'*'<a else'e'in f(i)+f(i)]

The iterFungsi adalah cara yang baik untuk membuat string input ke dalam antrian FIFO yang ingat berapa banyak string telah diurai di panggilan dari f. Ini idempoten, jadi tidak ada salahnya untuk menyebutnya lagi ketika input sudah menjadi iterator daripada string. Setengah dari jawaban yang dimulai dengan or'oe'... sepertinya itu memang golf, tapi aku tidak bisa menemukan apa pun.

-1 terima kasih kepada Sp3000.

feersum
sumber
Solusi hebat! Fungsi rekursif menggunakan itersangat mengejutkan pikiran saya.
xnor
3
Berikut adalah cara untuk menghitung aritmatika secara langsung dengan eval:def f(s,e=0,o=1):i=iter(s);a=next(i);return'eo'[eval(a*(a>'a')or f(i)+a+f(i))%2]
xnor
1
@ xnor Anda mungkin juga mempostingnya sebagai jawaban. Jauh berbeda dari solusi ini.
feersum
9

Mathematica, 91 84 byte

#//.s_:>s~StringReplace~{"+ee"|"+oo"|"*ee"|"*eo"|"*oe"->"e","+eo"|"+oe"|"*oo"->"o"}&

Mencari cara untuk kompres ini ...

LegionMammal978
sumber
3
//.lebih pendek dari FixedPoint.
alephalpha
8

Python 2, 80 byte

def f(s,e=0,o=1):i=iter(s);a=next(i);return(a>'a')*a or'eo'[eval(f(i)+a+f(i))%2]

Ini dibangun di atas jawaban yang sangat cerdik dari feersum yang menggunakan a iteruntuk mengimplementasikan operasi notasi Polandia. Gagasan baru adalah untuk digunakan evaluntuk mengevaluasi ekspresi +dan *dengan eval(f(i)+a+f(i)), di mana operator aditempatkan infiks antara hasil rekursif. Eval menggunakan binding e=0,o=1dalam argumen fungsi opsional. Output kemudian diambil mod 2.

Tidak
sumber
Ini juga bekerja di python 3. Ngomong-ngomong, bagaimana eval membutuhkan binding "e = 0, o = 1"?
karhell
@karhell Mengevaluasi ekspresi seperti e+o, jadi perlu variabel untuk merujuk ke angka.
xnor
8

C, 79 byte

Rekursi langsung. Bergantung pada beberapa properti bitwise (kebetulan?) Dari empat karakter input yang diizinkan.

f(){int c=getchar();return c&4?c:c&1?f()^f()^'e':f()&f();}main(){putchar(f());}
Ruud Helderman
sumber
8

Utilitas Shell + GNU, 33

dc -eFo`rev|tr oe OK`2%p|tr 10 oe

Masukan diambil dari STDIN.

Ini melakukan trik yang sama untuk membalikkan input dan mengevaluasi dengan kalkulator berbasis tumpukan - dalam hal ini dc. Kita bisa mengganti edan odengan 0dan 1, tetapi kemudian spasi perlu dimasukkan untuk mencegah penguraian angka yang serakah ke angka yang salah.

Sebaliknya ediganti dengan Kyang merupakan dcperintah untuk mendorong presisi saat ini ke tumpukan, yang secara default adalah 0. Dan odiganti dengan Oyang merupakan dcperintah untuk mendorong basis keluaran saat ini ke tumpukan. Ini perlu aneh, jadi kita atur ke 15 dengan Fosebelum melakukan hal lain di dc.

Maka itu hanya masalah mengambil mod 2 dan mencetak 2%p. Satu-satunya nilai yang mungkin sekarang 0dan 1, jadi tidak masalah bahwa basis output adalah 15. Kemudian trditerjemahkan kembali ke oatau e.


Saya suka itu jika Anda memicingkan mata, sumber ini hampir seperti dc Forever OK.

Trauma Digital
sumber
5

Serius , 24 byte

,R'2'e(Æ'1'o(Æ£ƒ'e'o2(%I

Manipulasi tumpukan yang lebih efisien mungkin bisa membuat ini lebih pendek, tapi meh, saya senang dengan itu.

Mengambil input sebagai string, misalnya "+*oee"

Coba online (input harus dimasukkan secara manual)

Penjelasan:

,R        get input and reverse it
'2'e(Æ    replace all "e"s with "2"s
'1'o(Æ    replace all "o"s with "1"s
£ƒ        cast as function and call
'e'o2(%I  push "e" if result is even, else "o"
Mego
sumber
5

Ruby, 61 byte

Menggunakan parsing keturunan rekursif dan aljabar boolean.

def f
gets(1)==?+?f^f : ~/\*/?f&f : $_==?o
end
puts f ? ?o:?e

Fungsi membaca satu karakter dari stdin sekaligus. Jika berbunyi a +atau a *, ia menyebut dirinya dua kali untuk menentukan ganjil atau genap. Fungsi kembali trueuntuk ganjil dan falseuntuk even. Operator ^ XOR dan & AND digunakan untuk menentukan "keanehan" dari penambahan dan ekspresi perkalian masing-masing.

Berikut ini adalah versi yang tidak dikoleksi:

def f
  x = gets(1)
  case x
  when '+'
    f ^ f
  when '*'
    f & f
  else
    x == 'o'
  end
end

puts f ? 'o' : 'e'

Terima kasih @Shel untuk menunjukkan bug di versi awal.

daniero
sumber
1
Ini tidak berhasil, +eememberi o. Saya suka ide itu
Shelvacu
ganti f^fdengan !f^fdan f&fdengan f|fdan berfungsi. Program untuk menjalankan test case: pastebin.com/ufXfd1vc
Shelvacu
1
Terima kasih, tangkapan bagus! Sepertinya saya agak bingung sendiri. Suite tes yang bagus juga! Tes-driven adalah cara untuk pergi, juga saat bermain golf :)
daniero
@Shel Aha ..! Saya berubah kembali f^fdan f&fmembalik $_==?edan ?e:?osebaliknya :)
daniero
1
Wow, pelajari sesuatu yang baru setiap hari ... ruby-doc.org/core/Regexp.html#method-i-7E
Shelvacu
4

Minkolang 0,14 , 40 byte

Saya mencoba melakukan metode eval yang cerdik, tetapi ternyata setiap nilai yang ditambahkan ke kotak kode di luar ruang asli tidak akan pernah tercapai oleh penghitung program. Jadi saya melakukan metode eval yang kurang pintar. : P

$o"eo+*"r0I4-[4g1Z2*1F]l*"e"+O.
0f1f+f*f

Coba di sini.

Penjelasan

$o                                Read in whole input as characters
  "eo+*"                          Push these characters onto the stack (in reverse order)
        r                         Reverse the stack
         I4-                      Push the length of the stack - 4
            [                     For loop; pop n and repeat that many times
             4g                   Get the item at the fourth index and put it on top
               1Z                 Pops n and pushes first index of n in stack
                 2*               Multiply by 2
                   1F             Gosub; goes to codebox(2n,1) to be returned to
                     ]            Close for loop
                      l*          Multiply by 10
                        "e"+      Add 101 ("o" is 111)
                            O.    Output as character and stop.
0f1f+f*f                          Does the appropriate operation then returns to F
El'endia Starman
sumber
1
Woo hoo! good ol 'shell beats a (semi-) bahasa golf ;-P
Digital Trauma
4

JavaScript, 110 106 94 byte

while(i.length>2)i=i.replace(/([+*][eo]{2})/,(o,e)=>{return"+oe+eo*oo".indexOf(o)<0?"e":"o"});

Tentu saja bukan solusi terkecil, tetapi kemungkinan solusi terkecil dalam bahasa verbal seperti JavaScript!

Arkain
sumber
Menggunakan grup yang tidak menangkap adalah baik untuk kinerja tetapi buruk untuk ukuran kode. Lebih baik hapus itu ?:.
manatwork
setuju ... dan dimodifikasi.
Arkain
Melihat sekali lagi sekarang. Kode Anda dapat dikurangi sedikit lebih jauh ke while(i.length>2)i=i.replace(/[+*][eo]{2}/,function(o){return"+oe+eo*oo".indexOf(o)>=0?"o":"e"}). Atau jika Anda mengubah ke fungsi panah gemuk ECMAScript 6, maka while(i.length>2)i=i.replace(/[+*][eo]{2}/,o=>"+oe+eo*oo".indexOf(o)>=0?"o":"e"). Namun sayangnya persyaratan mengatakan program atau fungsi, sedangkan kode Anda saat ini adalah cuplikan. Ini harus menangani input dan output atau argumen dan mengembalikan nilai.
manatwork
1
Sayangnya untuk valid di situs ini, kami tidak dapat mengasumsikan bahwa variabel sudah ada. Anda harus membuatnya berfungsi iseperti yang Anda katakan.
Alex A.
1
@Arkain, Anda tidak perlu menangkap grup dalam ekspresi reguler karena Anda akan tetap menggunakan seluruh substring yang cocok sebagai satu bagian. Untuk alasan yang sama tidak perlu meneruskan parameter e ke callback.
manatwork
4

O , 24 20 19 18 byte

i`2:e;1:o;~2%'o'e?

Mengambil input, membalikkannya, menetapkan eke 2 dan oke 1 dan mempostingnya ke Tumblr untuk mengevaluasinya sebagai kode O.

Penjelasan:

i` Dapatkan input dan balikkan, karena O menggunakan notasi postfix
2: e; Tetapkan `e` ke 2
1: o; Tetapkan `o` ke 1
~ 2% Eval dan periksa apakah hasilnya genap
'kan? Keluarkan 'e' jika genap, 'o' jika aneh
tahap
sumber
4

GNU Sed, 36

:
s/*oo\|+eo\|+oe/o/
t
s/\W\w\w/e/
t

Setelah posting saya melihat ini persis pendekatan yang sama seperti @ manatwork ini Perl jawaban dan @ randomra Retina jawaban . Jadi saya kira saya sebaiknya pergi jauh-jauh dan meminjamnya \W\w\wjuga.

Terima kasih kepada @Ruud karena mencukur 4 byte.

Trauma Digital
sumber
Dengan tanda kurung hilang, sekarang terbayar untuk meninggalkan regexp diperpanjang. Anda menang 2 byte karena tidak melarikan diri +, Anda kehilangan 2 byte karena melarikan diri |, tetapi hasil akhirnya adalah Anda memenangkan 1 byte untuk opsi menjatuhkan -r.
Ruud Helderman
@Ruud Benar. Saya sudah mencobanya sebelumnya, tetapi tidak menyadari |kebutuhan untuk melarikan diri ketika -rtidak digunakan. Namun, 2 byte lagi dari skor - terima kasih!
Digital Trauma
2

Haskell, 160 byte

Panggil f.

f=until((==1).l)r
r s|l s<3=s|3#s?o=r('o':3%s)|3#s?sequence["+*","oe","oe"]=r('e':3%s)|0<1=1#s++r(1%s)
l=length
(#)=take
(%)=drop
(?)=elem
o=["+eo","+oe","*oo"]
Leif Willerts
sumber
2

JavaScript, 92 71 byte

f=i=>i>"0"?i:f(i.replace(/.[eo]{2}/,e=>"eo"[eval((e[1]>"e")+"^&"[+(e[0]<"+")]+(e[2]>"e"))]))

Ini agak dikaburkan, tapi saya ingin melakukan sesuatu menggunakan evaloperator dan bitwise. Beranotasi:

f = (i) => // function(i) { return
    i>"0"  // i[0] == "o" || i[0] == "e" :-) - the characters `*` and `+` are both <"0"
      ? i  // finish
      : f(i.replace( // recursively repeat with
          /.[eo]{2}/, // first occurrence of "something" followed by two values
          (e) =>    // replaced by
              "eo"[ // string indexing
                eval(
                    (e[1]>"e")        // e[1] == "o" ? "true" : "false"
                  + "^&"[+(e[0]<"+")] // e[0] == "+" ? "^" : "&"
                  + (e[2]>"e")        // e[2] == "o" ? "true" : "false"
                )
              ]     // like eval(…) ? "o" : "e"
        ))

Pengulangan (e[…]>"e")sedikit mengganggu saya, tetapi berikut ini juga tidak lebih baik (103 byte):

f=i=>i>"0"?i:f(i.replace(/e|o/g,x=>+(x>"e")).replace(/.\d\d/,e=>"eo"[eval(e[1]+"^&"[+(e[0]<"+")]+e[2])]))

Jadi pada akhirnya, pendekatan @ Arkain dengan pencocokan substring sederhana adalah unggul. Dibuat menjadi fungsi, dengan beberapa optimisasi:

f=i=>i>"0"?i:f(i.replace(/.[eo]{2}/,v=>"eo"[+"+oe+eo*oo".includes(v)]))
Bergi
sumber
1

Dart, 173 byte

f(i){var l=i.split(''),e='e',o='o';g(p){if(l[p]!=e&&l[p]!=o){var x=p+1,y=p+2;g(x);g(y);l[p]=l[p]=='+'?l[x]!=l[y]?o:e:l[x]==o?l[y]:e;l.removeRange(x,p+3);}}g(0);print(l[0]);}

Ini tidak kompetitif, tetapi apa pun itu. Inti dari solusinya adalah, mulai dari 0, secara rekursif mengganti setiap operator dengan evaluasi pasangan karakter mengikuti operator itu dan kemudian menghapus karakter-karakter tersebut dari daftar.

Nick
sumber
1

Haskell, 231 byte

Berikut ini pendekatan menggunakan bahasa yang serius;)

Versi golf:

p(s:_)[]=s
p s(x:y)=p(r$x:s)y
r[]=[]
r('e':'e':'+':x)=r$'e':x
r('e':'o':'+':x)=r$'o':x
r('o':'e':'+':x)=r$'o':x
r('o':'o':'+':x)=r$'e':x
r('e':'e':'*':x)=r$'e':x
r('e':'o':'*':x)=r$'e':x
r('o':'e':'*':x)=r$'e':x
r('o':'o':'*':x)=r$'o':x
r x=x

Contoh:

*Main> p [] "+**+***+**++**+eooeoeeoeeoeooeo"
'o'

Versi tidak digabungkan dan cukup komprehensif:

type Stack = String

parse :: String -> Char
parse = parse' []

parse' :: Stack -> String -> Char
parse' (s:_) []     = s
parse' s     (x:xs) = parse' (reduce $ x:s) xs

reduce :: Stack -> Stack
reduce [] = []
reduce ('e':'e':'+':xs) = reduce $ 'e':xs
reduce ('e':'o':'+':xs) = reduce $ 'o':xs
reduce ('o':'e':'+':xs) = reduce $ 'o':xs
reduce ('o':'o':'+':xs) = reduce $ 'e':xs
reduce ('e':'e':'*':xs) = reduce $ 'e':xs
reduce ('e':'o':'*':xs) = reduce $ 'e':xs
reduce ('o':'e':'*':xs) = reduce $ 'e':xs
reduce ('o':'o':'*':xs) = reduce $ 'o':xs
reduce xs               = xs

Contoh:

*Main> parse "+**+***+**++**+eooeoeeoeeoeooeo"
'o'

Fitur: Pencocokan pola dan rekursi.

pengguna3389669
sumber
1

Jolf, 11 byte

(Noncompetitive, karena bahasa memposting pertanyaan.) Coba di sini!

FVyAi"oe"@\x12

(Ganti \x12dengan karakter sebenarnya \x12. Ini harus dilakukan secara otomatis dalam juru bahasa.)

Penjelasan:

FVyAi"oe"@\x12
    i          input
          \x12 character 12
         @     char code at
   A "oe"      replace all os with 1s and all es with 2s
  y            eval as jolf, returning the answer
 V             return parity "even" or "odd"
F              get first character
               implicit output
Conor O'Brien
sumber
1

Python 3, 171 145 135 byte

Tidak kompetitif, tetapi saya senang melakukannya, jadi saya tidak bisa menyimpannya sendiri. Tidak seperti entri Python rekursif-iterator (sangat pintar) oleh feersum , entri ini membalikkan input dan kemudian melakukan parsing berbasis tumpukan yang baik dari notasi Polandia terbalik.

def p(i):
 s=[]
 for c in i[::-1]:
  s+=[c>'e'if c>'a'else getattr(s.pop(),'__'+('axnodr'[c>'*'::2])+'__')(s.pop())]
 return'eo'[s[0]]
Tim Pederick
sumber
Itu callable()elegan, tapi panjang. (Membalikkan kondisi dan menghapus notakan lebih pendek.) Periksa sebaliknya jika m adalah bilangan bulat m in[0,1]akan lebih pendek, tetapi memeriksa apakah c adalah nilai c in'eo'akan lebih pendek. Ini nantinya sama dengan c>'a'dalam kasus ini.
manatwork
Sebenarnya tidak perlu untuk variabel m dan nilai numeriknya. Masukkan hanya ini di dalam for:s+=[c>'e'if c>'a'else{'*':o.and_,'+':o.xor}[c](s.pop(),s.pop())]
manatwork
@manatwork: Terima kasih! Saya tidak berpikir saya bisa membalikkan kondisinya, karena saya pikir itu berarti memanggil s.pop()(dua kali) setiap loop. Saya tidak repot-repot menguji sampai sekarang; tapi hei, intinya diperdebatkan sekarang.
Tim Pederick
Satu pertanyaan menggangguku sejak awal: mengapa menggunakan operator modul? bool.__and__()dan bool.__xor__()yang handier: s+=[c>'e'if c>'a'else getattr(s.pop(),{'*':'__and__','+':'__xor__'}[c])(s.pop())]. Namun berdasarkan gnibbler 's ujung mengiris , yang dapat diubah menjadi s+=[c>'e'if c>'a'else getattr(s.pop(),'__'+('axnodr'[c>'*'::2])+'__')(s.pop())].
manatwork
@Manatwork: Karena saya belum memikirkan itu. Saya hanya mempertimbangkan operator infiks ( ^, &) dan operatorrekanannya, lupa tentang metode yang benar-benar mengimplementasikannya. Oh, dan reversed()sekarang telah dibatalkan berkat tips golf Python lainnya .
Tim Pederick
1

Haskell, 98 94 byte

Maaf mengganggu Anda dengan upaya Haskell yang lain; hanya ingin membuktikannya sangat mungkin dalam waktu kurang dari 100 byte.

p(c:s)|any(<'a')s=p(c:p s)
p('+':x:y:s)|x/=y='o':s
p('*':'o':s)=s
p(c:_:_:s)|c<'a'='e':s
p s=s

Menentukan fungsi p yang menerima ekspresi apa pun yang valid sebagai parameter, dan mengembalikan hasilnya sebagai string dengan panjang 1.

Contoh:

*Main> p "**o++*ee*++eoe*eo+eoo"
"o"

Fungsi ini bekerja dengan mengurangi berulang-ulang operator paling kanan dalam string sampai tidak ada operator yang tersisa.

Ruud Helderman
sumber
0

Tambahkan ++ , 46 byte

D,g,@,d"oe"$eA"e"=+o
D,f,@,bR€gbU32CjbV2%"eo":

Cobalah online!

Footer hanya menyebutkan semua input contoh dan output yang sesuai.

Bagaimana itu bekerja

Seperti kehilangan jawaban di sini, ini menggunakan penggantian dan evaluasi. Fungsi utama kami adalah f, dan gmerupakan fungsi pembantu. Kami akan menggunakan "*e*o*e*oe"(yang e) sebagai contoh.

fdimulai dengan mengambil string input dan membalikkannya, menghasilkan "eo*e*o*e*". Kami kemudian memetakan gsetiap elemen:

gdimulai dengan menduplikasi argumen, untuk menyimpan salinan hingga perintah terakhir. Kami kemudian memeriksa apakah argumennya ada dalam string "oe", menghasilkan 1 untuk huruf dan 0 untuk *atau +. Kami kemudian mendorong argumen lagi dan memeriksa apakah itu sama dengan "e". Hasil ini kemudian ditambahkan ke cek sebelumnya. Ini menghasilkan 0 untuk salah satu *atau +, 1 untuk odan 2 untuk e. Kami kemudian mengambil OR logis antara nilai ini dan argumen. Jika nilainya 0 , diganti dengan argumen (yaitu *atau +), jika tidak dibiarkan apa adanya (yaitu 1 dan 2 ).

Ini mengubah semua huruf dalam kebalikan dari input menjadi nilai numerik. Kami kemudian menggabungkan setiap elemen dengan spasi, untuk memastikan angka tidak digabungkan. Sebagai contoh kita, ini menghasilkan string "2 1 * 2 * 1 * 2 *". Kita kemudian dapat mengevaluasi ini, menggunakan notasi postfix Add ++, menghasilkan 8 . Kami kemudian mengambil paritas dari nilai ini, menghasilkan 0 untuk bilangan genap dan 1 untuk bilangan ganjil, sebelum mengindeks ke dalam string "eo"dan mengembalikan huruf yang sesuai.

caird coinheringaahing
sumber