fork(19) download
  1. ############################################################################
  2. # Pyth version 1.0.1 #
  3. # 6-24-2014 #
  4. # Changes from 1.0.0: Added backslash, improved sum, added [_], removed #
  5. # str(), because repr() exists. ' is now in, ] is now [_], out of #
  6. # similarity to }. #
  7. # #
  8. # This python program is an interpreter for the pyth programming language. #
  9. # It is still in development - expect new versions often. #
  10. # #
  11. # To use, provide pyth code on one line of stdin. #
  12. # Further input on further lines. #
  13. # Prints out resultant python code for debugging purposes, then runs the #
  14. # pyth program. #
  15. # #
  16. # More information: #
  17. # The parse function takes a string of pyth code, and returns a single #
  18. # python expression ready to be executed. #
  19. # general_parse is the same but for multiple expressions. #
  20. # This program also defines the built-ins that the resultant expression #
  21. # uses, once expanded. #
  22. ############################################################################
  23.  
  24. def parse(code,spacing="\n "):
  25. assert type(code)==type('')
  26. # If we've reached the end of the string, give up.
  27. if len(code)==0:
  28. return '',''
  29. # Separate active character from the rest of the code.
  30. active_char=code[0]
  31. rest_code=code[1:]
  32. # Deal with numbers
  33. if active_char in ".0123456789":
  34. output=active_char
  35. while (len(rest_code)>0
  36. and rest_code[0] in ".0123456789"
  37. and (output+rest_code[0]).count(".")<=1):
  38. output+=rest_code[0]
  39. rest_code=rest_code[1:]
  40. return output,rest_code
  41. # String literals
  42. if active_char=='"':
  43. output=active_char
  44. while (len(rest_code)>0
  45. and output.count('"')<2):
  46. output+=rest_code[0]
  47. rest_code=rest_code[1:]
  48. if output[-1]!='"':
  49. output+='"'
  50. return output,rest_code
  51. # Python code literals
  52. if active_char=='$':
  53. output=''
  54. while (len(rest_code)>0
  55. and rest_code[0]!='$'):
  56. output+=rest_code[0]
  57. rest_code=rest_code[1:]
  58. return output,rest_code[1:]
  59. # End paren is magic.
  60. if active_char==')':
  61. return '',rest_code
  62. # Backslash is more magic.
  63. if active_char=='\\':
  64. if rest_code=='':
  65. return '',''
  66. else:
  67. return '','\\'+rest_code
  68. # Designated variables
  69. if active_char in variables:
  70. return active_char,rest_code
  71. # Now for the two letter variables/functions
  72. if active_char=='#':
  73. assert len(rest_code)>0
  74. return rest_code[0]*2,rest_code[1:]
  75. # And for general functions
  76. global c_to_f
  77. global next_c_to_f
  78. if active_char in c_to_f or active_char==',':
  79. if active_char==',':
  80. func_name=rest_code[0]*2
  81. init_paren=True
  82. arity=-1
  83. rest_code=rest_code[1:]
  84. else:
  85. func_name,arity=c_to_f[active_char]
  86. init_paren = (active_char not in no_init_paren)
  87. # Swap what variables are used in the map, filter or reduce.
  88. if active_char in next_c_to_f:
  89. c_to_f[active_char]=next_c_to_f[active_char]
  90. next_c_to_f[active_char]=c_to_f[active_char]
  91. # Recurse until terminated by end paren or EOF
  92. # or received enough arguments
  93. args_list=[]
  94. parsed='Not empty'
  95. while len(args_list) != arity and parsed != '':
  96. parsed,rest_code=parse(rest_code)
  97. args_list.append(parsed)
  98. # Build the output string.
  99. py_code=func_name
  100. if init_paren:
  101. py_code+='('
  102. if len(args_list)>0 and args_list[-1]=='':
  103. args_list=args_list[:-1]
  104. py_code+=','.join(args_list)
  105. py_code+=')'
  106. return py_code,rest_code
  107. # General format functions/operators
  108. # Also, comment characters, \, \n and \t
  109. if active_char in c_to_i:
  110. infixes,arity=c_to_i[active_char]
  111. args_list=[]
  112. parsed='Not empty'
  113. while len(args_list) != arity and parsed != '':
  114. parsed,rest_code=parse(rest_code)
  115. args_list.append(parsed)
  116. # Statements that cannot have anything after them
  117. if active_char in end_statement:
  118. rest_code=")"+rest_code
  119. py_code=infixes[0]
  120. for i in range(len(args_list)):
  121. py_code+=args_list[i]
  122. py_code+=infixes[i+1]
  123. return py_code, rest_code
  124. # Statements:
  125. if active_char in c_to_s:
  126. # Handle the initial portion (head)
  127. infixes,arity=c_to_s[active_char]
  128. args_list=[]
  129. parsed='Not empty'
  130. while len(args_list) != arity and parsed != '':
  131. parsed,rest_code=parse(rest_code)
  132. args_list.append(parsed)
  133. part_py_code=infixes[0]
  134. for i in range(len(args_list)):
  135. part_py_code+=args_list[i]
  136. part_py_code+=infixes[i+1]
  137. # Handle the body - return ends object as well.
  138. assert rest_code != ''
  139. args_list=[]
  140. parsed='Not empty'
  141. while parsed != '':
  142. parsed,rest_code=parse(rest_code,spacing+' ')
  143. args_list.append(parsed)
  144. # Trim the '' away and combine.
  145. if args_list[-1]=='':
  146. args_list=args_list[:-1]
  147. all_pieces=[part_py_code]+args_list
  148. return spacing.join(all_pieces),rest_code
  149. print("Something's wrong.")
  150. print("Current char is ",active_char)
  151. print("The rest of the code is ",rest_code)
  152. raise NotImplementedError
  153.  
  154. import random
  155. import copy
  156. import string
  157. # Function library, descriptions of everything.
  158. # += # ~ Y
  159. # repr # ` Y
  160. def _not(a):return not a # ! Y
  161. # _[_] # @ Y
  162. # # is special - 2 character variable Y
  163. # $ is special - python literal Y
  164. def mod(a,b):return a%b # % Y
  165. # pow # ^ Y
  166. # and # & Y
  167. def times(a,b):return a*b # * Y
  168. def _tuple(*a):return a # ( Y
  169. # ) is special - end extensible Y
  170. def minus(a,b):return a-b # - Y
  171. def neg(a):return -a # _ Y
  172. def plus(a,b):return a+b # + Y
  173. # = deepcopy # = Y
  174. copy = copy.deepcopy
  175. def _list(*a):return list(a) # [ Y
  176. # set # { Y
  177. # [_] # ] Y
  178. # dict # } Y
  179. # or # | Y
  180. # break out of all containing Y
  181. # slice # : Y
  182. def pop(a):return a.pop() # ; Y
  183. # in # ' Y
  184. # " is special - string literal Y
  185. # , is special - 2 character function Y
  186. def lt(a,b):return a<b # < Y
  187. # . is special - numbers # . Y
  188. def gt(a,b):return a>b # > Y
  189. def div(a,b):return a//b # / Y
  190. # if else # ? Y
  191. # 0-9 are special - numbers # 0-9 Y
  192. # (x) #| | Y
  193. # all # A Y
  194. # .append() # a Y
  195. # break # B Y
  196. b="\n" # b Y
  197. # chr # C Y
  198. def count(a,b):return a.count(b) # c Y
  199. # def # D Y
  200. # variable - associated with map # d Y
  201. d='"'
  202. # else # E Y
  203. def lower(a):return a.lower() # e Y
  204. # for # F Y
  205. def _filter(a,b): # f Y
  206. return list(filter(a,b))
  207. # variable - associated with reduce # G Y
  208. G=string.ascii_lowercase
  209. def gte(a,b):return a>=b # g Y
  210. # variable - associated with reduce # H Y
  211. H={}
  212. def read_file(): # h Y
  213. a="\n".join(open(input()))
  214. return a
  215. # h assigns the text of the user
  216. # inputted file to the variable given.
  217. # if # I Y
  218. def _round(a,b=None): # i Y
  219. if b is None:
  220. return float(a)
  221. if b is 0:
  222. return int(a)
  223. return round(a,b)
  224. # designated function # J Y
  225. def join(a,b):return a.join(b) # j Y
  226. # designated function # K Y
  227. k='' # k Y
  228. def lte(a,b):return a<=b # L Y
  229. # len # l Y
  230. # max # M Y
  231. def _map(a,b):return list(map(a,b)) # m Y
  232. N=None # N Y
  233. # min # n Y
  234. def rand(a,b): # O Y
  235. return random.randint(a,b)
  236. # ord # o Y
  237. def split(a,b=None): # P Y
  238. if b:
  239. return a.split(b)
  240. else:
  241. return a.split()
  242. # print # p Y
  243. def quotient(a,b):return a/b # Q Y
  244. def equal(a,b):return a==b # q Y
  245. # return # R Y
  246. def _range(a,b=None): # r Y
  247. if b:
  248. return list(range(a,b))
  249. else:
  250. return list(range(a))
  251. # sorted # S Y
  252. def _sum(a):
  253. return reduce(lambda b,c:b+c,a) # s Y
  254. # T is associated with filter # T Y
  255. T=10
  256. def tail(a):return a[1:] # t Y
  257. def upper(a):return a.upper() # U Y
  258. def reduce(a,b): # u Y
  259. acc=b[0]
  260. seq=b[1:]
  261. while len(seq)>0:
  262. h=seq[0]
  263. acc=a(acc,h)
  264. seq=seq[1:]
  265. return acc
  266. def rev(a): return a[::-1] # V Y
  267. # eval(parse # v Y
  268. # while # W Y
  269. # input # w Y
  270. def index(a,b): # X Y
  271. if b in a:
  272. return a.index(b)
  273. # replicate functionality from str.find
  274. else:
  275. return -1
  276. # exec(general_parse # x Y
  277. Y=[] # Y Y
  278. # any # y Y
  279. Z=0 # Z Y
  280. def _zip(a,b):return list(zip(a,b)) # z Y
  281.  
  282. no_init_paren='fmu'
  283. end_statement='BR'
  284. variables='bdGHkNTYZ'
  285.  
  286. # To do: even preassociated variables deserve to be initialized.
  287. # Variables cheat sheet:
  288. # b = "\n"
  289. # d is for map, d='"'
  290. # G is for reduce, G=string.ascii_lowercase (abc..xyz)
  291. # H is for reduce, H = {}
  292. # k = ''
  293. # N = None, second option variable for map,filter,reduce
  294. # T is for filter, second variable option for reduce, T=10
  295. # Y = []
  296. # Z = 0
  297.  
  298. c_to_s={
  299. 'D':(('def ',':'),1),
  300. 'E':(('else:'),0),
  301. 'F':(('for ',' in ',':'),2),
  302. 'I':(('if ',':'),1),
  303. 'W':(('while ',':'),1),
  304. }
  305. # Arbitrary format operators - use for assignment, infix, etc.
  306. # All surrounding strings, arity
  307. c_to_i={
  308. '\\':(('',''),1),
  309. '\n':(('',''),1),
  310. '\t':(('',''),1),
  311. '~':(('','+=',''),2),
  312. '@':(('','[',']'),2),
  313. '&':(('(',' and ',')'),2),
  314. '|':(('(',' or ',')'),2),
  315. '=':(('','=copy(',')'),2),
  316. ']':(('[',']'),1),
  317. "'":(('(',' in ',')'),2),
  318. '?':(('(',' if ',' else ',')'),3),
  319. 'a':(('','.append(',')'),2),
  320. 'B':(('break',),0),
  321. 'h':(('','=read_file()'),1),
  322. 'R':(('return ',''),1),
  323. 'x':(('exec(general_parse(','))'),1),
  324. }
  325.  
  326. # Simple functions only.
  327. # Extensible is allowed, nothing else complicated is.
  328. # -1 means extensible
  329. # name,arity
  330. c_to_f={
  331. '`':('repr',1),
  332. '!':('_not',1),
  333. '%':('mod',2),
  334. '^':('pow',2),
  335. '*':('times',2),
  336. '(':('_tuple',-1),
  337. '-':('minus',2),
  338. '_':('neg',1),
  339. '+':('plus',2),
  340. '[':('_list',-1),
  341. '{':('set',1),
  342. '}':('dict',0),
  343. ':':('slice',2),
  344. ';':('pop',1),
  345. '<':('lt',2),
  346. '>':('gt',2),
  347. '/':('div',2),
  348. ' ':('',1),
  349. 'A':('all',1),
  350. 'C':('chr',1),
  351. 'c':('count',2),
  352. 'e':('lower',1),
  353. 'f':('_filter(lambda T:',2),
  354. 'g':('gte',2),
  355. 'i':('_round',2),
  356. 'J':('J',-1),
  357. 'j':('join',2),
  358. 'K':('K',-1),
  359. 'L':('lte',2),
  360. 'l':('len',1),
  361. 'M':('max',1),
  362. 'm':('_map(lambda d:',2),
  363. 'O':('rand',0),
  364. 'o':('ord',1),
  365. 'P':('split',2),
  366. 'p':('print',1),
  367. 'Q':('quotient',2),
  368. 'q':('equal',2),
  369. 'r':('_range',2),
  370. 'S':('sorted',1),
  371. 's':('_sum',1),
  372. 't':('tail',1),
  373. 'U':('upper',1),
  374. 'u':('reduce(lambda G,H:',2),
  375. 'V':('rev',1),
  376. 'v':('eval',1),
  377. 'w':('input',0),
  378. 'X':('index',2),
  379. 'z':('_zip',2),
  380. }
  381.  
  382. # Gives next function header to use - for filter, map, reduce.
  383. next_c_to_f={
  384. 'f':('_filter(lambda N:',2),
  385. 'm':('_map(lambda N:',2),
  386. 'u':('reduce(lambda N,T',2),
  387. }
  388. assert set(c_to_f.keys())&set(c_to_i.keys())==set()
  389. # Run it!
  390. def general_parse(code):
  391. args_list=[]
  392. parsed='Not empty'
  393. while parsed != '':
  394. parsed,code=parse(code)
  395. # Necessary for backslash not to infinite loop
  396. if code and code[0]=='\\':
  397. code=code[1:]
  398. args_list.append(parsed)
  399. # Build the output string.
  400. py_code='\n'.join(args_list[:-1])
  401. return py_code
  402. code=input()
  403. py_code=general_parse(code)
  404. print(py_code)
  405. print('='*50)
  406. exec(py_code)
Success #stdin #stdout 0.16s 12264KB
stdin
=ZvwpfAmq1lf'NTdZu+Gm+N]HG+]]YmN{sZ
[[1, 3, 4, 7], [1, 2, 5, 6], [3, 4, 8], [8, 9]]
stdout
Z=copy(eval(input()))
print(_filter(lambda T:all(_map(lambda d:equal(1,len(_filter(lambda N:(N in T),d))),Z)),reduce(lambda G,H:plus(G,_map(lambda N:plus(N,[H]),G)),plus([[Y]],_map(lambda N:N,set(_sum(Z)))))))
==================================================
[[1, 8], [2, 7, 8], [5, 7, 8], [6, 7, 8], [2, 3, 9], [2, 4, 9], [3, 5, 9], [4, 5, 9], [3, 6, 9], [4, 6, 9]]