On Wed, Sep 07, 2005 at 03:00:29PM -0400, Stevan Little wrote: : If methods and subs are in the same namespace, and both have the & : sigil, what about instance attributes and class attributes? Is this : legal? : : class Foo { : my $.bar; : has $.bar; : } : : Part of me thinks that it should be since my $.bar is an attribute of : the Foo class, and has $.bar is an attribute of instances of Foo.
I don't think that should be any more legal than { my $foo; our $foo; } since both declarations are trying to install the same symbol in a scope regardless of the actual scope/lifetime of the variable in question. The difference is that with the latter, the collision is in the lexical scope, while in the former, the collision is in the package's method name space. The problem is you're making two .bar accessors in the same scope, even if the things being accessed are in different places. It's also a problem under my current view that Foo (the non-meta class) is primarily just the undefined prototype instance, in which case you don't want to make artificial distinctions between the type of Foo itself and the type of its instances. So I think that if .can is true for an instance method it should also be true of the class method, even if it would fail when used on the class object (because it's undefined, not because it's a different type). This fits with the policy that we want to be able to use class names to reason about class behavior generically even in the absence of an actual instance. Foo.can('bar') needs to be true regardless of whether you said "my" or "has". : Also, is there anyway to iterate over the keys in the namespace? The : old way would be to do something like keys(%Foo::). Is something like : this possible with the new way? Sure, it's still just a hash, basically, so Foo.keys() works fine. All we've changed is that we've removed a special syntactic case by allowing a type/package object to pretend to be a hash when used that way, just as we allow it to pretend to be an undef when used as an instance. Tagmemics strikes again... Of course, this is not entirely free, insofar as the Hash role has to figure out when it's being composed into a class, and pick an entirely different behavior when used as a class name than when used as an instance of the class. That is, Foo{$x} wants to do a symbol table lookup, while (new Foo){$x} has to access the Hash interface of the instance. But still think I'd rather hide the semantic fudge down there than bake it into special syntax, even though it means being a wee bit inconsistent about the type relationship of Foo and (new Foo). Or if that ends up causing too much indigestion, we could still back off to a Foo::{$x} syntax without requiring % on the front. After all, the main point of the change is to get rid of the sigil on the front of things like $CALLER::_ so that we end up with CALLER<$_> instead. So CALLER::<$_> wouldn't be all that bad if we decide the bare package name is too ambiguous in its semantics. Then we'd probably see things like ::($pkg)::<$var> ::($pkg)::{$varname} Hmm, unless we actually spring for infix:<::> to get $pkg :: '$var' $pkg :: $varname But I think that makes symbolic references a little too easy to use, and a little too hard to spot. Though I suppose that's no worse than the current proposal allowing $pkg<$var> $pkg{$varname} Maybe what we really have is a class of *postfix* operators that all begin with ::, as in ::(...) ::<...> ::{...} Basically steal the :: from the old %Foo:: syntax, and analyze it the other way. Then a name is simply not allowed to end with ::. Postfix operators are recognized where an operator is expected. But if a term can start with ::(), maybe it can start with ::<> or ::{} as well. Not quite sure if that makes sense. We could make it mean something. Doubtless term ::<$foo> should mean the same as $foo though. Term ::{$varname} is probably just MY::{$varname}, and also likely to be confused with ::($sym). So that approach doesn't really buy us much. So let's just try to make the simple Foo<$var> form stick for now, and back off later if forced to. Larry