Previous section   Next section

Practical Programming in Tcl & Tk, Third Edition
By Brent B. Welch

Table of Contents
Chapter 5.  Tcl Lists

Constructing Lists

Constructing a list can be tricky because you must maintain proper list syntax. In simple cases, you can do this by hand. In more complex cases, however, you should use Tcl commands that take care of quoting so that the syntax comes out right.

The list command

The list command constructs a list out of its arguments so that there is one list element for each argument. If any of the arguments contain special characters, the list command adds quoting to ensure that they are parsed as a single element of the resulting list. The automatic quoting is very useful, and the examples in this book use the list command frequently. The next example uses list to create a list with three values, two of which contain special characters.

Example 5-1 Constructing a list with the list command.
set x {1 2}
=> 1 2
set y foo
=> foo
set l1 [list $x "a b" $y]
=> {1 2} {a b}foo
set l2 "\{$x\\a b}$y"
=> {1 2} {a b}foo


The list command does automatic quoting.

Compare the use of list with doing the quoting by hand in Example 5-1. The assignment of l2 requires carefully constructing the first list element by using quoted braces. The braces must be turned off so that $x can be substituted, but we need to group the result so that it remains a single list element. We also have to know in advance that $x contains a space, so quoting is required. We are taking a risk by not quoting $y because we know it doesn't contain spaces. If its value changes in the future, the structure of the list can change and even become invalid. In contrast, the list command takes care of all these details automatically.

When I first experimented with Tcl lists, I became confused by the treatment of curly braces. In the assignment to x, for example, the curly braces disappear. However, they come back again when $x is put into a bigger list. Also, the double quotes around a b get changed into curly braces. What's going on? Remember that there are two steps. In the first step, the Tcl parser groups arguments. In the grouping process, the braces and quotes are syntax that define groups. These syntax characters get stripped off. The braces and quotes are not part of the value. In the second step, the list command creates a valid Tcl list. This may require quoting to get the list elements into the right groups. The list command uses curly braces to group values back into list elements.

The lappend Command

The lappend command is used to append elements to the end of a list. The first argument to lappend is the name of a Tcl variable, and the rest of the arguments are added to the variable's value as new list elements. Like list, lappend preserves the structure of its arguments. It may add braces to group the values of its arguments so that they retain their identity as list elements when they are appended onto the string representation of the list.

Example 5-2 Using lappend to add elements to a list.
lappend new 1 2
=> 1 2
lappend new 3 "4 5"
=> 1 2 3 {4 5}
set new
=> 1 2 3 {4 5}

The lappend command is unique among the list-related commands because its first argument is the name of a list-valued variable, while all the other commands take list values as arguments. You can call lappend with the name of an undefined variable and the variable will be created.

The lappend command is implemented efficiently to take advantage of the way that Tcl stores lists internally. It is always more efficient to use lappend than to try and append elements by hand.

The concat Command

The concat command is useful for splicing lists together. It works by concatenating its arguments, separating them with spaces. This joins multiple lists into one list where the top-level list elements in each input list become top-level list elements in the resulting list:

Example 5-3 Using concat to splice lists together.
set x {4 5 6}
set y {2 3}
set z 1
concat $z $y $x
=> 1 2 3 4 5 6

Double quotes behave much like the concat command. In simple cases, double quotes behave exactly like concat. However, the concat command trims extra white space from the end of its arguments before joining them together with a single separating space character. Example 5-4 compares the use of list, concat, and double quotes:

Example 5-4 Double quotes compared to the concat and list commands.
set x {1 2}
=> 1 2
set y "$x 3"
=> 1 2 3
set y [concat $x 3]
=> 1 2 3
set s { 2 }
=>  2
set y "1 $s 3"
=> 1  2  3
set y [concat 1 $s 3]
=> 1 2 3
set z [list $x $s 3]
=> {1 2} { 2 } 3

The distinction between list and concat becomes important when Tcl commands are built dynamically. The basic rule is that list and lappend preserve list structure, while concat (or double quotes) eliminates one level of list structure. The distinction can be subtle because there are examples where list and concat return the same results. Unfortunately, this can lead to data-dependent bugs. Throughout the examples of this book, you will see the list command used to safely construct lists. This issue is discussed more in Chapter 10.

      Previous section   Next section