Skip to content
VLSI Mentor

Tcl Part I · Module 6 · Lists

What a Tcl List Actually Is

Lists are the data structure Tcl is built around, and the first thing to understand about them is the thing most surprising to anyone arriving from another language: a list is not a separate kind of value. It is a string, written in a particular format, and the list commands are commands that read a string according to that format. This is not a technicality — it explains why lists compose so freely with text, why a value can be counted two different ways, and why building one carelessly produces something that is quietly not the list you meant.

Foundation12 min readTclPart IListsMental Model

Part I · Module 6 · Chapter 6.1 · What a Tcl List Actually Is

1. The Claim

A Tcl list is a string whose words follow list rules.

Not a string underneath. Not convertible to a string. It is one.

2. The Proof

Azvya Education Pvt. Ltd.VLSI Mentor
proof.tcl
set items [list a b c]

puts "the value:     <$items>"
puts "string length: [string length $items]"
puts "llength:       [llength $items]"
puts "equals \"a b c\"? [expr {$items eq "a b c"}]"
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
the value:     <a b c>
string length: 5
llength:       3
equals "a b c"? 1

Read the last line again. [list a b c] produced a value that is exactly equal to the five characters a b c — compared with eq, which from Chapter 4.4 compares characters and never anything else.

There is no list object. There are five characters, and llength knows how to count the words in them.

3. This Is Chapter 3.1 Again

Chapter 3.1 established the model: a value carries text, and the command that reads it decides what it means. Lists are one such reading.

Azvya Education Pvt. Ltd.VLSI Mentor
two-readings.tcl
set v "clk 1 input"

puts "as text: [string length $v] characters, first character <[string index $v 0]>"
puts "as list: [llength $v] elements, first element <[lindex $v 0]>"
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
as text: 11 characters, first character <c>
as list: 3 elements, first element <clk>

One value, two commands, two entirely reasonable answers.

Two parallel left-to-right flows. The value clk 1 input is read by string length, which answers eleven characters, and by llength, which answers three elements.The valueclk 1 inputstring lengthcounts charactersAnswer: 11spaces includedThe same valueclk 1 inputllengthcounts elementsAnswer: 3words, by list rules12
Figure 1 — one value, two readings. The same eleven characters are counted as text by string length and as elements by llength. Neither reading is stored in the value; each command applies its own rules to the same characters. This is why the output of one command can be fed to another without any conversion step.

4. What "List Rules" Means

The format is the one you already know from Chapter 2.3 — the same word-splitting rules Tcl uses when reading a command:

  • Whitespace separates elements.
  • Braces group an element that contains spaces.
  • Runs of whitespace count as one separator, unlike split — Chapter 5.13 §5.
Azvya Education Pvt. Ltd.VLSI Mentor
rules.tcl
puts "simple:        [llength {a b c}]"
puts "extra spaces:  [llength {a   b     c}]"
puts "braced element:[llength {a {b c} d}]"
puts "nested:        [lindex {a {b c} d} 1]"
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
simple:        3
extra spaces:  3
braced element:3
nested:        b c

The third list has three elements, the middle one being the two words b c held together by braces.

5. Not Every String Is a List

Here is the half the slogan leaves out:

Azvya Education Pvt. Ltd.VLSI Mentor
not-a-list.tcl
set bad "a {b c"

puts [catch {llength $bad} message]
puts $message
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
1
unmatched open brace in list

An unbalanced brace means the text cannot be read as a list, and llength says so rather than guessing.

So the accurate statement is:

Every list is a string. Not every string is a list.

Most ordinary text happens to be a valid list — "clk 1 input" is three elements, "hello" is one. It is braces and quotes that can make text unreadable as a list, which is precisely why Chapter 6.2 insists you build lists with list rather than by gluing text together.

6. Why This Design Is Useful

Because lists are strings, every command that accepts text accepts a list:

Azvya Education Pvt. Ltd.VLSI Mentor
composing.tcl
set items [list alpha beta gamma]

puts "as a list:   [llength $items] elements"
puts "as text:     [string toupper $items]"
puts "searched:    [string first "beta" $items]"
puts "still a list:[llength [string toupper $items]]"
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
as a list:   3 elements
as text:     ALPHA BETA GAMMA
searched:    6
still a list:3

The uppercase version is still a perfectly good three-element list, because uppercasing did not disturb the spaces.

In a language with a distinct list type you would be converting at every boundary. Here there is no boundary.

7. The Empty List

Azvya Education Pvt. Ltd.VLSI Mentor
empty.tcl
set empty {}

puts "llength:       [llength $empty]"
puts "string length: [string length $empty]"
puts "is empty text? [expr {$empty eq ""}]"
Azvya Education Pvt. Ltd.VLSI Mentor
Snippet
llength:       0
string length: 0
is empty text? 1

The empty list and the empty string are the same value. {} and "" are two ways of writing it.

Most code uses {} when the intent is a list and "" when the intent is text. The convention communicates; Tcl does not distinguish.

8. Common Mistakes

Looking for a list type. There is none. §1.

Assuming any string can be used as a list. Unbalanced braces cannot. §5.

Building a list by gluing text together. Chapter 6.2 is entirely about why.

Mixing text operations and list operations on the same value carelessly. §6.

Expecting split and list parsing to agree on whitespace. They do not — Chapter 5.13 §5.

9. Exercises

Exercise 1 — prove it yourself. Build a three-element list with list, print it, and show with eq that it equals the plain text you would have typed.

Exercise 2 — two readings. For the value "a bb ccc", print the character count and the element count, and the first of each.

Exercise 3 — the rules. Predict the element count of each, then check: {x y z}, {x y z}, {x {y z}}, {{x y} {z}}, {}.

Exercise 4 — break it. Create a string with an unmatched brace and pass it to llength. Read the error. Then make it valid and confirm it works.

Exercise 5 — the composing edge. Take a three-element list, apply string map {" " "-"} to it, and print the new element count. Explain what happened.

Exercise 6 — empty. Show that {} and "" are the same value, using eq, llength and string length.

10. Remember

  • A Tcl list is a string whose words follow list rules. [list a b c] equals the characters a b c.
  • There is no list type, and no conversion step between text and lists.
  • List rules are the same word-splitting rules Tcl uses for commands — whitespace separates, braces group, runs of whitespace count once.
  • Every list is a string; not every string is a list. Unbalanced braces cannot be read as one.
  • Any text command accepts a list, which is why they compose freely.
  • But a text operation can change the element count without an error. Do not alternate carelessly.
  • The empty list and the empty string are the same value. Write {} when you mean a list.

Next: the one command that builds a list correctly, and what happens when you do not use it.

Where this fits

Part of the Tcl curriculum.