Tcl $argc and $argv variables
Solution 1
You appear to make two wrong assumptions here:
If a proc does not use a special argument
args
in its defintion (see below for more info), it accepts only the fixed number of arguments—exactly matching the number of parameters used in its definition. Each call is checked by the interpreter, and any call with invalid number of parameters will fail before reaching the procedure's code itself.See for yourself:
% proc foo {a b c} {} % foo wrong # args: should be "foo a b c" % foo 1 wrong # args: should be "foo a b c" % foo 1 2 3 4 wrong # args: should be "foo a b c" % foo 1 2 3 %
In other words, just don't mess with trying to check the number of arguments passed to your
proc
: it's already checked by the interpreter by the time your procedure is called.The
argc
andargv
global variables control what's passed from the operating system to the Tcl interpreter program which is executing your Tcl script.That is, when you call something like
$ tclsh myscript.tcl foo bar
The variable named
argc
will contain 2 andargv
will be set to the list containing two strings—"foo" and "bar".In other words, these variables have nothing to do with individual procedures.
Regarding the args
special argument: if a procedure uses the word "args" for the last of its arguments or has it as its sole argument, then this argument is turned into a list which consumes any number (including zero) of actual arguments.
So you can do
proc foo {a b args} {}
and then your foo
procedure can be called as both like foo 1 2
and foo 1 2 3 4 5 6
but not like foo x
(because there's no value for the b
formal argument).
Inside such a proc you use normal list commands (like llength
and lindex
) to inspect whatever is contained in args
. For instance, the call foo 1 2 3 4 5 6
would set args
to the same value you would obtain by calling [list 3 4 5 6]
.
Solution 2
The argc
and argv
variables are global variables (when they have any special meaning). Inside a procedure, they're not special at all unless you say:
global argc argv
or use the fully-qualified versions.
With your procedure, you will get an error message (generated by the procedure call machinery) unless you pass in the right number of arguments. You don't need to check yourself (unless you use formal parameters with defaults or the special args
variable — note the spelling — at the end of the formal parameters.
To get the exact list of arguments passed in to your procedure, use:
set allArguments [info level 0]
You normally don't need it. You definitely don't need it when declaring your procedure like:
proc TestVerb { Data Data_txt } {
...
}
Flaxter
Updated on June 27, 2022Comments
-
Flaxter almost 2 years
I'm kinda new to tcl but I have to write a proc that looks like this:
proc TestVerb { Data Data_txt } { VERBATIM [format "// Data: $Data - $Data_txt"] if { $argc == 2} { VERBATIM {// SUCCESS //} else { exit 1 }
I call the proc like this:
TestVerb Switch"This is used for..."
The proc is in a different file and the proc call is in another one. They seem properly sourced because I get the desired output if I do not use
$argc
but once I use either$argv
or$argc
I get the following compilation error: Can't read$argv/$argc
no such variableIf I refer to this variables with
$::argc
and$::argv
the result is not correct.$argv
is empty and $argc is 0 -
Flaxter over 9 yearsHello, Thanks for the quick answer. The point is that proc will be used by other people and I need to check the number of arguments they have given to it and if it's not correct to exit; I've already tried using global argv argc But I still get incorrect output: argv <blank> argc 0