питон, 197 символов в неясной версии.
Читаемая версия: 369 символов. Нет анализа, прямой анализ.
import random
def dice(s):
return sum(term(x) for x in s.split('+'))
def term(t):
p = t.split('*')
return factor(p[0]) if len(p)==1 else factor(p[0])*factor(p[1])
def factor(f):
p = f.split('d')
if len(p)==1:
return int(f)
return sum(random.randint(1, int(g[1]) if g[1] else 6) for \
i in range(int(g[0]) if g[0] else 1))
сжатая версия: 258 символов, однозначные имена, некорректные условные выражения, ярлык в логическом выражении:
import random
def d(s):
return sum(t(x.split('*')) for x in s.split('+'))
def t(p):
return f(p[0])*f(p[1]) if p[1:] else f(p[0])
def f(s):
g = s.split('d')
return sum(random.randint(1, int(g[1] or 6)) for i in range(int(g[0] or 1))) if g[1:] else int(s)
неясная версия: 216 символов, используя Reduce, сильно отображаются, чтобы избежать «def», «return».
import random
def d(s):
return sum(map(lambda t:reduce(lambda x,y:x*y,map(lambda f:reduce(lambda x,y:sum(random.randint(1,int(y or 6)) for i in range(int(x or 1))), f.split('d')+[1]),t.split('*')),1),s.split('+')))
Последняя версия: 197 символов, сложенные в комментариях @ Brain, добавлены тестовые прогоны.
import random
R=reduce;D=lambda s:sum(map(lambda t:R(int.__mul__,map(lambda f:R(lambda x,y:sum(random.randint(1,int(y or 6))for i in[0]*int(x or 1)),f.split('d')+[1]),t.split('*'))),s.split('+')))
Тесты:
>>> for dice_expr in ["3d6 + 12", "4*d12 + 3","3d+12", "43d29d16d21*9+d7d9*91+2*d24*7"]: print dice_expr, ": ", list(D(dice_expr) for i in range(10))
...
3d6 + 12 : [22, 21, 22, 27, 21, 22, 25, 19, 22, 25]
4*d12 + 3 : [7, 39, 23, 35, 23, 23, 35, 27, 23, 7]
3d+12 : [16, 25, 21, 25, 20, 18, 27, 18, 27, 25]
43d29d16d21*9+d7d9*91+2*d24*7 : [571338, 550124, 539370, 578099, 496948, 525259, 527563, 546459, 615556, 588495]
Это решение не может обрабатывать пробелы без соседних цифр. поэтому «43d29d16d21 * 9 + d7d9 * 91 + 2 * d24 * 7» будет работать, а «43d29d16d21 * 9 + d7d9 * 91 + 2 * d24 * 7» - из-за второго пробела (между «+» и « г "). Это можно исправить, сначала удалив пробелы из s, но это сделает код длиннее 200 символов, поэтому я оставлю ошибку.