88For example \\ alpha will tab autocomplete to α.
99"""
1010
11+ import difflib
1112import lark
1213import kdrag .smt as smt
1314from lark import Tree
6263theorem : "theorem" NAME ":" expr ":=" "grind"
6364
6465NAME: /[a-zA-Z_][a-zA-Z0-9_']*/
65- NUMBER: /-?\d+/
66+ NUMBER: /-?\d+(\.\d+)? /
6667%import common.WS
6768%ignore WS
6869COMMENT: "--" /[^\n]*/
@@ -82,7 +83,25 @@ def __getitem__(self, key):
8283 elif key in self .globals :
8384 return self .globals [key ]
8485 else :
85- raise KeyError (key )
86+ # Suggest a close name in error
87+ names = list (self .locals ) + list (self .globals )
88+ dotted = []
89+ for name , value in self .globals .items ():
90+ if name .startswith ("_" ):
91+ continue
92+ try :
93+ attrs = dir (value )
94+ except Exception :
95+ continue
96+ for attr in attrs :
97+ if attr .startswith ("_" ):
98+ continue
99+ dotted .append (f"{ name } .{ attr } " )
100+ hints = difflib .get_close_matches (str (key ), names + dotted , n = 3 , cutoff = 0.6 )
101+ msg = f"Unknown name { key !s} "
102+ if hints :
103+ msg += f". Did you mean: { ', ' .join (hints )} ?"
104+ raise NameError (msg )
86105
87106 def __setitem__ (self , key , value ):
88107 self .locals [key ] = value
@@ -166,7 +185,10 @@ def expr(tree, env: Env) -> smt.ExprRef:
166185 match tree :
167186 # TODO: obviously this is not well typed.
168187 case Tree ("num" , [n ]):
169- return int (n ) # type: ignore
188+ text = str (n )
189+ if "." in text :
190+ return smt .RealVal (text )
191+ return int (text )
170192 case Tree ("const" , [name , * attrs ]):
171193 res = env [name ] # type: ignore
172194 for attr in attrs :
0 commit comments