0

I am getting an error invalid character "." while running following code in tcl shell :

set var "p.txt_bc"
set p.txt_bc 1
expr $$var

invalid character "." in expression "$p.txt_bc"

How to handle the "." character here so that the output is 1 ? I know I can replace the "." with something else to somehow make it work but is there a way to get the expected output without any substitution done to "." ?

slebetman
  • 109,858
  • 19
  • 140
  • 171

1 Answers1

1

The $$var doesn't do double substitution. It puts a $ in front of the contents of var. That results in the literal expression $p.txt_bc, which is syntactically invalid because . isn't an operator in Tcl's expression language.

To do double substitution, you should use [set] for the outer layer (and brace your expression so that Tcl can compile it, please), like this:

expr { [set $var] }

However, experience suggests that there are usually better approaches than using double substitution. In particular, most cases are better addressed by using either associative arrays or upvar.

set var "p.txt_bc"
set data(p.txt_bc) 1
expr { $data($var) }
set var "p.txt_bc"
set p.txt_bc 1
upvar 0 $var v
expr { $v }

The version with upvar is more common when the variable is in a different scope to the current one, and upvar 0 isn't really recommended at the global level as it isn't easy to undo (because most operations on variables work on the alias as if it was the target).

Donal Fellows
  • 133,037
  • 18
  • 149
  • 215
  • We have discussed doing double substitution with `$$`, but have always decided not to as it encourages confusing usage. It would also break some existing code, but that wasn't the core consideration. – Donal Fellows Oct 29 '22 at 10:28
  • Also, once you use `[set $...]`, you probably don't need `expr` round the outside. Unless you want the "try to convert the result to a standard form number if you can but no worries if you can't" semantics. – Donal Fellows Oct 31 '22 at 09:31