Compiler/lexical analyzer: Difference between revisions

m
Read from stdin instead of from a file.
m (Fix a bug in make-this-or-that-handler and use lisp keywords instead of obscure symbols.)
m (Read from stdin instead of from a file.)
Line 1,822:
*readtable*))
 
(defun lex-string (stringstream)
(loop with *readtable* = (make-lexer-readtable)
(with-input-from-string (s string)
(loop with *readtable*eof = (make-lexer-readtablegensym)
with counting-stream = (make-instance 'counting-character-input-stream :stream stream)
with eof = (gensym)
for with streamtoken = (make-instanceread 'counting-character-input-stream :streamnil seof)
until for(eq token = (read stream nil eof)
do (format untilt (eq"~5D ~5D token~15A~@[ eof)~S~]~%"
(token-line token) (token-column token) (token-name token) (token-value token))
dofinally (format t "~5D ~5D ~15A~@[ ~S~]~%"
(token-line token) (token-column token) (token-name token) (token-value token))
(line-of counting-stream) (column-of counting-stream) :end-of-input)
finally (format t "~5D ~5D ~15A~%"
(line-ofclose stream) (columncounting-of stream) :end-of-input))
(close stream))))
 
(defun lex (file)
(with-open-file (s file)
(let* ((buffer (make-array (file-length s) :element-type 'character
:fill-pointer t))
(pos (read-sequence buffer s)))
(setf (fill-pointer buffer) pos)
(lex-string buffer))))
 
(defun main ()
(lex *standard-input*))</lang>
(let ((file (uiop:command-line-arguments)))
(if file
(lex file)
(error "File must be specified"))))</lang>
{{out|case=test case 3}}
<pre> 5 16 KEYWORD-PRINT
68

edits