www.gibmonks.com




  Previous section   Next section

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

Table of Contents
Chapter 14.  Namespaces


Notes

The final section of this chapter touches on a variety of features of the namespace facility.

Names for Widgets, Images, and Interpreters

There are a number of Tcl extensions that are not affected by the namespaces described in this chapter, which apply only to commands and variable names. For example, when you create a Tk widget, a Tcl command is also created that corresponds to the Tk widget. This command is always created in the global command namespace even when you create the Tk widget from inside a namespace eval block. Other examples include Tcl interpreters, which are described in Chapter 19, and Tk images, which are described in Chapter 38.

The variable command at the global scope

It turns out that you can use variable like the global command if your procedures are not inside a namespace. This is consistent because it means "this variable belongs to the current namespace," which might be the global namespace.

Auto Loading and auto_import

The following sequence of commands can be used to import commands from the foo package:

package require foo
namespace import foo::*

However, because of the default behavior of packages, there may not be anything that matches foo::* after the package require. Instead, there are entries in the auto_index array that will be used to load those procedures when you first use them. The auto loading mechanism is described in Chapter 12. To account for this, Tcl calls out to a hook procedure called auto_import. This default implementation of this procedure searches auto_index and forcibly loads any pending procedures that match the import pattern. Packages like [incr Tcl] exploit this hook to implement more elaborate schemes. The auto_import hook was first introduced in Tcl 8.0.3.

Namespaces and uplevel

Namespaces affect the Tcl call frames just like procedures do. If you walk the call stack with info level, the namespace frames are visible. This means that you can get access to all variables with uplevel and upvar. Level #0 is still the absolute global scope, outside any namespace or procedure. Try out Call_Trace from Example 13-5 on page 180 on your code that uses namespaces to see the effect.

Naming Quirks

When you name a namespace, you are allowed to have extra colons at the end. You can also have two or more colons as the separator between namespace name components. These rules make it easier to assemble names by adding to the value returned from namespace current. These all name the same namespace:

::foo::bar
::foo::bar::
::foo:::::::bar

The name of the global namespace can be either :: or the empty string. This follows from the treatment of :: in namespace names.

When you name a variable or command, a trailing :: is significant. In the following command a variable inside the ::foo::bar namespace is modified. The variable has an empty string for its name!

set ::foo::bar:: 3
namespace eval ::foo::bar { set {} }
=> 3

If you want to embed a reference to a variable just before two colons, use a backslash to turn off the variable name parsing before the colons:

set x xval
set y $x\::foo
=> xval::foo

Miscellaneous

You can remove names you have imported:

namespace forget random::init

You can rename imported procedures to modify their names:

rename range Range

You can even move a procedure into another namespace with rename:

rename random::init myspace::init

      Previous section   Next section
    Top