THIS IS VERY VERY DRAFTY (so lots of bugs flew in) Package-like things (they are namespaces) [todo - rationalize when to say "namespace" vs "package"] Kinds of packages: Structure Adds ------------------------------------------------------------- Package namespace, traits, autoload +- Module export/import, version +- Role methods, attributes, inheritance, parameterized +- Class methods, attributes, composition, instantiation +- Enum weird methods Name and duration: Syntax Name Name visibility Duration -------------------------------------------------------------------------- package P top-level global until exit or deletion my package P top-level lexical dynamic? our package P relative to same as same as current package (?) package anonymous n/a dynamic Scope of declaration ... package P; ... # to end of enclosing scope ... package P {...} # block scope ... package {...} # block scope Same for modules, classes, roles?, enums?, subtypes? But grammars and rules have a separate system. Names Names are hierarchical, like filesystem path names. They start with :: . The separator is also :: . Just like / in unix. Strings can be interpolated into names by ($expr) , but must begin and end at separator boundaries. Special namespaces ::* global (root) ::MY current lexical ::CALLER a view of the caller's namespace ::*::Main the user default A name N can be used: N by itself %N:: as a hash (symbol table) $N @N %N &N to name variables The beginning of a name can be abbreviated, to make short names even simpler. Example Shorter Rule --------------------------------------------------------------------------- %::A %A Starting :: can be dropped if not at the word beginning ::*::A ::*A Root doesn't need a separator ::A A Declared name doesn't need the starting :: ::*A *A Root's starting :: can be dropped where there is no confusion with unary * (such as declarations). There are a bunch of examples below. A single hierarchy is shared by modules, classes, roles, enums, and subtypes. [yes?] Grammars and rules use the same separator, but otherwise have a separate system. Relative package names are searched for - from inner lexical scopes to outer, then - from inner packages to outer, then - in the global namespace. [this deserves elaboration] Autoloading The presense of names in a namespace can be faked. Or implemented lazily. If a user inquires about (defined(...)), or tries to use a variable, which is not in the symbol table, hooks are called. For SCALAR ARRAY HASH SUB METH ...: AUTO... predicates test the existance of a variable, returning undef or _any_ ref of the right type. AUTO...DEF accessors actually fetch the requested variable. [Can a package or role AUTOMETH?] Binding := ::= # todo Examples ::A namespace name, relative ::A::B ::A::B::C ::* namespace name, absolute (::* is root) ::*A (root doesn't need a separator) ::*A::B ::*A::B::C %A:: namespace as hash; relative name %A::B:: %*:: namespace as hash; absolute name %*A:: %*A::B:: %x variable name, lexical ("%" could be any sigil $@%& etc) %A::x variable name, relative ("%" could be any sigil $@%& etc) %A::B::x ("%" could be any sigil $@%& etc) %*x variable name, absolute ("%" could be any sigil $@%& etc) %*A::x ("%" could be any sigil $@%& etc) %*A::B::x ("%" could be any sigil $@%& etc) Abbreviations used ::*::A ::*A # root doesn't need a separator %::A:: %A:: # leading :: is only needed if it starts the word # ::A::B could NOT be abbreviated A::B (??) %::A::x %A::x %::*::x %*x # using both %::*::A:: %*A:: Notable namespaces ::MY # current lexical namespace %MY:: # \__ as hash %MY::x # \__ a variable in ("%" could be any sigil $@%& etc) ::*Main # default user namespace %*Main:: # \__ as hash %*Main::x # \__ a variable in ("%" could be any sigil $@%& etc) Runtime interpolation: ::("A") ::A ::("A::B") ::A::B ::("A::")B # ILLEGAL ::("A")::B ::A::B ::A::("B") ::A::B ::A::("B")::C ::A::B::C ::("*") ::* ::("*A") ::*A ::("*::A") ::*A %::("A"):: %A:: %::("A::") # ILLEGAL %::("A::x") %A::x ("%" could be any sigil $@%& etc) ::($expr) a namespace name ::($e1)::($e2) a namespace name %::($expr):: a namespace used as a hash %::($expr) a variable name ("%" could be any sigil $@%& etc) Using a namespace hash (a symbol table): %P:: # namespace P as a hash (a symbol table) %P::<$s> # lookup $s %P::<@a> # lookup @a %P::{'$s'} # lookup $s again, just quoted differently. %P::{$sym} # lookup some symbol specified at runtime