Ну, это странно ... нет, подождите, это даже!

70

преамбула

Целые числа всегда либо четные, либо нечетные . Четные целые числа делятся на два, нечетные целые - нет.

Когда вы добавляете два целых числа, вы можете определить, будет ли результат четным или нечетным, основываясь на том, были ли слагаемые четными или нечетными:

  • Даже + Даже = Даже
  • Четный + Нечетный = Нечетный
  • Нечетный + Четный = Нечетный
  • Нечетный + Нечетный = Четный

Аналогично, когда вы умножаете два целых числа, вы можете сделать вывод, будет ли результат четным или нечетным, исходя из того, были ли факторы четными или нечетными:

  • Даже * даже = даже
  • Четный * Нечетный = Четный
  • Нечетный * Четный = Четный
  • Нечетный * Нечетный = Нечетный

Таким образом, если вы знаете четность или нечетность всех переменных в математическом выражении, которое включает только сложение и умножение, вы можете сделать вывод, будет ли результат четным или нечетным.

Например, мы можем с уверенностью сказать, что это (68 + 99) * 37приводит к нечетному, потому что четный плюс нечетный ( 68 + 99) является нечетным, и что нечетный раз другой нечетный ( odd * 37) дает нечетное.

Вызов

Напишите программу или функцию, которая принимает строку, содержащую только четыре символа eo+*. Эта строка представляет математическое выражение, данное в префиксной нотации, включающее только добавление ( +) и умножение ( *). Каждый eпредставляет некоторое произвольное четное число, и каждый oпредставляет некоторое произвольное нечетное число.

Ваша задача состоит в том, чтобы упростить выражение, распечатать или вернуть единичное eили oна основе того, является ли результат выражения четным или нечетным.

Вы можете предположить, что ввод всегда будет в действительной префиксной записи. В частности, каждый +и *всегда будет иметь два соответствующих операнда, следующих за ним. Эти операнды могут быть одним eили o, или другим, +или *выражением, которое, в свою очередь, имеет операнды.

Например, входные данные *+eooмогут быть прочитаны как mul(add(e, o), o), или (e + o) * oв нормальной записи инфикса . И eпервый o- операнды, соответствующие +, и +eoпоследний o- операнды, соответствующие *.

Просто чтобы прояснить ситуацию, вот некоторые недопустимые входные данные, которые имеют неправильную префиксную запись:

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

Единственный завершающий символ новой строки в выводе - это хорошо, но в противном случае все, что должно быть выведено, - это eчетное для четного или oнечетного.

Самый короткий код в байтах побеждает.

Тестовые случаи

(Пустые строки служат только для визуального разделения похожих случаев.)

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
Кальвин Хобби
источник
8
Можем ли мы взять 1 и 0 вместо e и o в качестве входных данных?
ghosts_in_the_code
8
@ ghosts_in_the_code Нет, извините.
Увлечения Кэлвина
2
Используете ли вы evalОК?
xnor
1
@xnor Конечно. Что бы ни работало.
Увлечения Кэлвина
2
Я сомневаюсь, что смогу использовать это, чтобы превзойти уже опубликованные 13 байтов, но я замечаю, что сложение соответствует исключающему или и умножению простому или.
WGroleau

Ответы:

43

CJam, 18 17 13 байтов

Спасибо aditsu за сохранение 4 байта.

qW:O%eu~"eo"=

Попробуйте тестовый набор здесь. (Набор тестов слишком длинный для постоянной ссылки. Просто скопируйте их из спецификации задачи.)

объяснение

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.
Мартин Эндер
источник
27

Pyth, 16 14 байтов

@"eo".vjdXzGU9

Pyth может сам оценивать строку, то есть в синтаксисе Pyth. Поэтому я заменяю eи oна 4и 5. Тогда оценка даст мне четное или нечетное число, и я легко смогу напечатать результат.

Попробуйте онлайн: демонстрация или тестовый набор

Объяснение:

@"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"

Дополнительное объяснение к замене. Gпеременная, инициализированная алфавитом abc...xyz. U9это список [0, 1, ..., 8]. XzGU9заменяет буквы алфавита значениями списка. Так aзаменяется 0, bс 1, ..., eс 4, ..., iс 8, jс 0, ... и oс 5. Поэтому меня eзаменяют четным числом и oнечетным числом. Все остальные замены не имеют никакого эффекта вообще.

Jakube
источник
Почему вы меняете выражение? Кроме того, вам не нужно брать результат по модулю 2, или индексирование оборачивается?
xnor
@xnor доступ к элементу в строке выполняется по модулю переноса. Так что нет необходимости по модулю 2.
Якуб
@xnor Но спасибо за обратную вещь. Конечно, это не обязательно. (Я немного устал сегодня.)
Jakube
16

Perl, 50 45 40 символов

(39 символов кода + 1 символ опции командной строки.)

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

Образец прогона:

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
источник
Как насчет while/../?
Прим
Doh. Я тупая На самом деле использовал это условие, пока пробовал его sedверсию ... Спасибо, @primo.
Манатворк
Или даже лучше 1while s/\+oe.... Я также уверен, что [+*]может быть заменен \W.
Примо
Еще раз спасибо, @primo. Я думаю, что я должен сосредоточиться на одном решении один раз. ( gemaсводит меня с ума…)
манатворк
Такой же подход с Sed теперь на 2 байта короче!
Цифровая травма
13

Сетчатка , 29 байт

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

Для удобной версии файла используется -sфлаг.

Мы поменяться нечетные выражения ( *oo, +oe, +eo) к , oпока мы не можем, а затем поменять оставшиеся символ буквы букв выражения e. Мы повторяем это до тех пор, пока не сможем, и последняя буква - это наш результат.

(Это решение похоже на Perl-ответ manatwork .)

Попробуйте онлайн! (Деннис)

randomra
источник
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)]

Эта iterфункция - хороший способ сделать входную строку в очередь FIFO, которая запоминает, какая часть строки была проанализирована при вызовах f. Он идемпотентен, поэтому безвредно вызывать его снова, когда входные данные уже являются итератором, а не строкой. Задняя половина ответа, начинающаяся с or'oe'... кажется, должна быть пригодной для игры в гольф, но я ничего не мог найти.

-1 благодаря Sp3000.

feersum
источник
Отличное решение! Рекурсивные функции с использованием iterдействительно ошеломляют мой разум.
xnor
3
Вот способ вычислить арифметику напрямую с помощью 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 Вы можете также опубликовать это как ответ. Это сильно отличается от этого решения.
feersum
9

Mathematica, 91 84 байта

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

Ищете способ сжать это ...

LegionMammal978
источник
3
//.короче чем FixedPoint.
алефальфа
8

Python 2, 80 байт

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]

Это основано на очень умном ответе feersum, который использует iterдля реализации операций польской нотации. Новая идея состоит в том, чтобы использовать evalдля вычисления выражений +и *с тем eval(f(i)+a+f(i)), где оператор aставит инфикс между рекурсивными результатами. Eval использует привязки e=0,o=1в необязательных аргументах функции. На выходе берется мод 2.

XNOR
источник
Это также работает в Python 3. Кстати, как eval нуждается в привязках "e = 0, o = 1"?
karhell
@karhell Он оценивает выражения как e+o, поэтому ему нужны переменные для ссылки на числа.
xnor
8

C, 79 байтов

Простая рекурсия. Полагается на некоторые (случайные?) Побитовые свойства четырех разрешенных входных символов.

f(){int c=getchar();return c&4?c:c&1?f()^f()^'e':f()&f();}main(){putchar(f());}
Рууд Хелдерман
источник
8

Утилиты Shell + GNU, 33

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

Ввод взят из STDIN.

Это делает ту же самую хитрость при обращении ввода и оценке с помощью стекового калькулятора - в этом случае dc. Мы могли бы заменить eи oна 0и 1, но тогда нужно было бы вставить пробелы, чтобы избежать жадного разбора цифр в неправильные числа.

Вместо eзаменяется Kкоторая является dcкомандой , чтобы подтолкнуть текущую точность в стек, который по умолчанию равно 0. А oзаменяется Oкоторая является dcкомандой , чтобы подтолкнуть текущую выходную базу в стек. Это должно быть странно, поэтому мы устанавливаем 15 с, Foпрежде чем делать что-либо еще в dc.

Тогда нужно просто взять мод 2 и распечатать 2%p. Единственными возможными значениями являются сейчас 0и 1, поэтому не имеет значения, что база вывода равна 15. Затем trпереводится обратно в oили e.


Мне нравится, что если ты прищуришься, этот источник выглядит почти так dc Forever OK.

Цифровая травма
источник
5

Серьезно , 24 байта

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

Более эффективные манипуляции со стеком, вероятно, могли бы сделать это короче, но я доволен этим.

Принимает ввод в виде строки, например "+*oee"

Попробуйте онлайн (ввод должен быть введен вручную)

Объяснение:

,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"
Мего
источник
5

Рубин, 61 байт

Использование рекурсивного синтаксического анализа и логической алгебры.

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

Функция читает один символ из стандартного ввода за раз. Если он читает a +или a *, он дважды вызывает себя, чтобы определить нечетное или четное. Функция возвращает trueдля нечетных и falseдля even. Операторы ^ XOR и & AND используются для определения «нечетности» выражений сложения и умножения соответственно.

Вот негольфированная версия:

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

puts f ? 'o' : 'e'

Спасибо @Shel за указание на ошибку в начальной версии.

daniero
источник
1
Это не работает, +eeдает o. Мне нравится идея
Shelvacu
заменить f^fна !f^fи f&fс, f|fи это работает. Программа для запуска тестовых случаев: pastebin.com/ufXfd1vc
Shelvacu
1
Спасибо, хороший улов! Кажется, я немного запутался там. Хороший набор тестов тоже! Тест-драйв - это то, что нужно, даже когда
играешь в
@Shel Ага ..! Я изменил назад f^fи f&fи перевернул $_==?eи ?e:?oвместо этого :)
Даниеро
1
Ух ты, узнай что-то новое каждый день ... ruby-doc.org/core/Regexp.html#method-i-7E
Шелваку
4

Минколанг 0,14 , 40 байт

Я попытался сделать умный метод eval, но оказалось, что любые значения, добавленные в кодовое поле за пределами исходного пространства, никогда не будут достигнуты счетчиком программы. Так что я сделал менее умный метод eval. :П

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

Попробуй это здесь.

объяснение

$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
Эльендия Старман
источник
1
Woohoo! хорошая старая оболочка бьет (полу) язык игры в гольф ;-P
Digital Trauma
4

JavaScript, 110 106 94 байта

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

Конечно, не самое маленькое решение, но, вероятно, самое маленькое из возможных решений в многословном языке, таком как JavaScript!

Arkain
источник
Использование групп без захвата хорошо для производительности, но плохо для размера кода. Лучше убери их ?:.
Манатворк
согласился ... и так изменил.
Аркейн
Взглянул еще раз. Ваш код может быть уменьшен немного дальше while(i.length>2)i=i.replace(/[+*][eo]{2}/,function(o){return"+oe+eo*oo".indexOf(o)>=0?"o":"e"}). Или, если вы переключитесь на функцию жирной стрелки ECMAScript 6, тогда while(i.length>2)i=i.replace(/[+*][eo]{2}/,o=>"+oe+eo*oo".indexOf(o)>=0?"o":"e"). Но, к сожалению, требование говорит о программе или функции, в то время как ваш текущий код является фрагментом. Он должен обрабатывать либо ввод и вывод, либо аргумент и возвращаемое значение.
manatwork
1
К сожалению, чтобы быть действительным на этом сайте, мы не можем предположить, что переменная уже существует. Вы должны будете сделать это функцией, iкак вы сказали.
Алекс А.
1
@ Arkain, вам не нужно захватывать группу в регулярном выражении, так как вы все равно будете использовать всю подобранную подстроку как одну часть. По той же причине нет необходимости передавать параметр e в обратный вызов.
Манатворк
4

О , 24 20 19 18 байт

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

Принимает входной сигнал, изменяет его, назначает eна 2 и oна 1 и сообщения его Tumblr оценивает его в качестве кода вывода.

Объяснение:

Я получаю ввод и полностью изменяю его, потому что O использует постфиксную нотацию
2: е; Назначьте `e` 2
1: а; Назначьте `o` 1
~ 2% Eval и проверьте, является ли результат четным
«O'e? Выведите «e», если четное, «o», если нечетное
фаза
источник
4

GNU Sed, 36

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

После отправки я увидел точно такой же подход , как @ manatwork - х Perl ответ и Retina ответ @ randomra в . Так что, я думаю, я могу пройти весь путь и позаимствовать их \W\w\w.

Спасибо @Ruud за то, что сбрил 4 байта.

Цифровая травма
источник
С удалением скобок теперь стоит отказаться от расширенного регулярного выражения. Вы выигрываете 2 байта за то, что не сбежали +, вы теряете 2 байта за побег |, но в итоге вы выигрываете 1 байт за опцию сброса -r.
Рууд Хелдерман
@ Рууд Правильно. Я пробовал это раньше, но не понимал, что |нужно избегать, когда -rне используется. Тем не менее, еще 2 байта вне счета - спасибо!
Цифровая травма
2

Haskell, 160 байт

Вызов 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"]
Лейф Виллертс
источник
2

JavaScript, 92 71 байт

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

Это немного запутано, но я хотел сделать что-то, используя evalпобитовые операторы. Аннотированный:

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"
        ))

Повторение (e[…]>"e")немного раздражает, но и следующее не лучше (103 байта):

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])]))

Итак, в конце концов, подход @ Arkain с простым сопоставлением подстрок превосходит все ожидания. Сделано в функцию, с некоторыми оптимизациями:

f=i=>i>"0"?i:f(i.replace(/.[eo]{2}/,v=>"eo"[+"+oe+eo*oo".includes(v)]))
Берги
источник
1

Дротик, 173 байта

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]);}

Это не конкурентоспособно, но что угодно. Суть решения состоит в том, чтобы, начиная с 0, рекурсивно заменить каждый оператор на оценку пары символов, следующих за этим оператором, а затем удалить эти символы из списка.

Ник
источник
1

Haskell, 231 байт

Вот подход с использованием серьезного языка;)

Гольф версия:

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

Пример:

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

Недоверчивая и довольно полная версия:

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

Пример:

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

Особенности: сопоставление с образцом и рекурсия.

user3389669
источник
1

Джольф, 11 байт

(Неконкурентоспособен, так как язык задвигает вопрос назад.) Попробуйте здесь!

FVyAi"oe"@\x12

(Заменить \x12на реальный символ \x12. Это должно быть сделано автоматически в интерпретаторе.)

Объяснение:

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
Конор О'Брайен
источник
1

Python 3, 171 145 135 байтов

Не конкурентоспособный, но я получал удовольствие, делая это, поэтому я просто не мог оставить это при себе. В отличие от (очень умной) записи Python для рекурсивных итераторов, созданной feersum , эта операция инвертирует ввод, а затем выполняет хороший старый стековый анализ обратной польской записи.

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]]
Тим Педерик
источник
Это callable()элегантно, но долго. (Изменение условия и удаление notбудет короче.) Вместо этого проверьте, является ли m целым числом m in[0,1], будет короче, но проверка, является ли значение c c in'eo', будет еще короче. Это позже так же, как и c>'a'в этом случае.
Манатворк
На самом деле нет необходимости в переменной m и ее числовых значениях. Поместите только это в for:s+=[c>'e'if c>'a'else{'*':o.and_,'+':o.xor}[c](s.pop(),s.pop())]
manatwork
@ Manatwork: Спасибо! Я не думал, что смогу отменить условие, потому что думал , что это означало бы вызов s.pop()(дважды) каждого цикла. Я не беспокоился о тестировании до сих пор; но эй, сейчас вопрос спорный.
Тим Педерик
С самого начала меня беспокоил один вопрос: зачем использовать operator модуль? bool.__and__()и bool.__xor__()являются сподручнее: s+=[c>'e'if c>'a'else getattr(s.pop(),{'*':'__and__','+':'__xor__'}[c])(s.pop())]. Но , основываясь на gnibbler «s нарезания наконечник , который может быть изменен в s+=[c>'e'if c>'a'else getattr(s.pop(),'__'+('axnodr'[c>'*'::2])+'__')(s.pop())].
manatwork
@ Manatwork: потому что я не думал об этом. Я рассматривал только инфиксные операторы ( ^, &) и их operatorаналоги, забывая о методах, которые на самом деле их реализуют. О, и reversed()теперь был исключен благодаря другим советам по игре в гольф от Python .
Тим Педерик
1

Haskell, 98 94 байта

Извините, что беспокою вас еще одной попыткой Haskell; просто хотел доказать, что это очень хорошо возможно менее чем за 100 байтов.

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

Определяет функцию, pкоторая принимает любое допустимое выражение в качестве параметра и возвращает результат в виде строки длиной 1.

Пример:

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

Функция работает путем многократного сокращения самого правого оператора в строке, пока не останется ни одного оператора.

Рууд Хелдерман
источник
0

Добавить ++ , 46 байт

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

Попробуйте онлайн!

Нижний колонтитул просто перечисляет все входные данные примера и их соответствующие выходные данные.

Как это устроено

Как потеря ответов здесь, это использует замену и оценку. Наша основная функция f, и gявляется вспомогательной функцией. Мы будем использовать "*e*o*e*oe"(что есть e) в качестве примера.

fначинается с взятия входной строки и обращения ее к результату "eo*e*o*e*". Затем мы сопоставляем gкаждый элемент:

gначинается с дублирования аргумента, чтобы сохранить копию до последней команды. Затем мы проверяем, находится ли аргумент в строке "oe", получая 1 для букв и 0 для *или +. Затем мы снова выдвигаем аргумент и проверяем, равен ли он "e". Этот результат затем добавляется к предыдущей проверке. Это дает 0 для либо *или +, 1 для oи 2 для e. Затем мы берем логическое ИЛИ между этим значением и аргументом. Если значение равно 0 , оно заменяется аргументом (то есть *или +), в противном случае оно остается как есть (то есть 1 и 2 ).

Это преобразует все буквы на обратной стороне ввода в числовое значение. Затем мы соединяем каждый элемент пробелами, чтобы гарантировать, что цифры не объединяются. Для нашего примера это дает строку "2 1 * 2 * 1 * 2 *". Затем мы можем оценить это, используя постфиксную нотацию Add ++, получив 8 . Затем мы берем четность этого значения, получая либо 0 для четных чисел, либо 1 для нечетных чисел, перед индексацией в строку "eo"и возвращением соответствующей буквы.

Caird Coneheringaahing
источник