eval
.
For instance
eval puts OKwould print the string OK. However,
eval puts Not OKwill generate an error.
The reason that the second command generates an error is
that the eval
uses concat
to merge its arguments
into a command string. This causes the two words Not OK
to
be treated as two arguments to puts
. If there is more
than one argument to puts
, the first argument must
be a file pointer.
Correct ways to write the second command include these:
eval [list puts {Not OK}] eval [list puts "Not OK"] set cmd "puts" ; lappend cmd {Not OK}; eval $cmd
As long as you keep track of how the arguments you present to eval
will be grouped, you can use many methods of creating the strings for eval
,
including the string
commands and format
.
The recommended methods of constructing commands for eval
is to use
the list
and lappend
commands. These commands become difficult
to use, however if you need to put braces in the command, as was done in the
previous lesson.
The example from the previous lesson is re-implemented in the example code using lappend.
The completeness of a command can be checked with info complete
.
Info complete
can also be used in an interactive program to determine if
the line being typed in is a complete command, or the user just entered a
newline to format the command better.
info complete
string
string
has no unmatched brackets, braces or
parentheses, then a value of 1 is returned, else 0 is returned.set cmd "OK" eval puts $cmd set cmd "puts" ; lappend cmd {Also OK}; eval $cmd set cmd "NOT OK" eval puts $cmd eval [format {%s "%s"} puts "Even This Works"] set cmd "And even this can be made to work" eval [format {%s "%s"} puts $cmd ] set tmpFileNum 0; set cmd {proc tempFileName } lappend cmd "" lappend cmd "global num; incr num; return \"/tmp/TMP.[pid].\$num\"" eval $cmd puts "\nThis is the body of the proc definition:" puts "[info body tempFileName]\n" set cmd {puts "This is Cool!} if {[info complete $cmd]} { eval $cmd } else { puts "INCOMPLETE COMMAND: $cmd" }