|
Perl 6
Perl 6 Variable Tablet: Revision 74
"Overview"[Perl 6 Tablets] - _Chapter:_ "0:Intr"[Perl 6 Intro Tablet], "1:Hist"[Perl 6 History Tablet], "2:Design"[Perl 6 Language Design Tablet], *"3:Var"[Perl 6 Variable Tablet]*, "4:Op"[Perl 6 Operator Tablet], "5:IO"[Perl 6 IO Tablet], "6:{}"[Perl 6 Block Tablet], "7:Sub"[Perl 6 Subroutine Tablet], "8:OOP"[Perl 6 OOP Tablet], "9:Rx"[Perl 6 Regex Tablet] - _Appendices:_ "A:Index"[Perl 6 Index Tablet], "B:Tables"[Perl 6 Lookup Tablet], "C:Cook"[Perl 6 Cookbook Tablet], "D:Delta"[Perl 6 Delta Tablet], "E:Best of"[Best Of Perl 6 Tablet], "F:Links"[Perl 6 Links Tablet]
---- {toc: } _"Allison Randal"<http://allisonrandal.com/>: The most basic building blocks of a programming language are its nouns, the chunks of data that get sucked in, pushed around, altered in various ways, and spat out to some new location._ ^ Primary Types Perl 6 (as Perl 5) knows 3 basic types of variables: "Scalars"{link: Scalar} (single values), "Arrays"{link: Array} (ordered and indexed lists of several values) and "Hashes"{link: Hash} (2 column table, with ID and associated value pairs). They can be easily distinguished, because in front of their name is a special character called "sigil"{link: [Perl 6 Lookup Tablet] Sigils} (latin for sign). Its the $ (similar to S) for Scalars, @ (like an a) for Arrays and a % (kv pair icon) for a Hash. They are now invariant (not changing), which means for instance, an array vaiable starts always with an @, even if you just want a slice of the content. The sigils mark also distinct namespaces, meaning: in one "lexical scope"{link: Scoping} you can have 3 different variables named $stuff, @stuff and %stuff. These sigils "can also be used as an operator"{link: [perl 6 lookup tablet] Contextualizers} to enforce a context in which the following data will be seen. The fourth namespace where you can store and retrieve something under specified names is the one of "subroutines and alike"{link: Callable}, even if you don't might think of them as variables. It's sigil & has to be used only rarely. Special namespaces of Perl 5 (often marked with special syntax) like tokens (__PACKAGE__), formats, file or dir handle and builtins are now regular (mostly scalar) variables or routines. Because variables are (as anything in Perl 6) "objects"[Perl 6 OOP Tablet], they have methods. In fact, "any operator"[Perl 6 Operator Tablet], including these square or curly brackets you get specific array and hash values with, are just methods of a variable object with a fancy name. The primary sigil can be followed by a secondary sigil, called "twigil, which mostly indicate special scope"{link: Twigils } of that variable. ^^ Scalar This type is known as a storage room for one value, but it's more like a reference that can point to anything: to values of any data type, to _code_, to _objects_ or to a compound of values like a "pair"{link: Pair}, "junction"{link: [perl 6 operator tablet] junctions}, "array"{link: Array}, "hash"{link: Hash} or "capture"{link: Capture}. The scalar context is now called item context hence the _scalar_ instruction from Perl 5 was renamed to "item"{link: [perl 6 lookup tablet] Contextualizers}. > $CHAPTER = 3; > $pi = 3.14159_26535_89793; # the underscores just ease reading > $float = 6.02e23; > $complex = 1+2i; > $text = 'Welcome all!'; # "single quoted string"{link: [perl 6 IO tablet] Single Quotes} > $text = {{"}} What is $pi?{{"}}; # "double quoted string"{link: [perl 6 IO tablet] Double Quotes}, does eval $pi to its content > $text = q:to'EOT'; # "heredoc string"{link: [perl 6 IO tablet] Heredocs} >> handy for multiline text >> like HTML templates or email > EOT > $handle = open $file_name; # "file handle"{link: [perl 6 IO tablet] Files} > $object = Class::Name.new(); > $arrayref = {{[0,1,1,2,3,5,8,13,21];}} > $hashref = {'audreyt'=>'pugs', 'pm'=>'pct', 'damian'=>'larrys evil henchman'}; > $coderef = sub { do_something_completely_diffenent(@_) }; Unlike Perl 5, references are automatically dereferenced to a fitting context. So you could use these $arrayref and $hashref in same way as an array or hash, making $ the variable highlighter, pretty much like in PHP. ^^ Array is an ordered and indexed list of "scalar variables"{link: Scalar}. If not specified otherwise, they can be changed, prolonged and shorten anytime and used as a list, stack, queue and much more. As in Haskell, lists are processed lazily, which means: the compiler looks only at the part he currently needs. This way Perl 6 can handle infinite lists or do computation on lists that are still building up. The _lazy_ command enforces and the _eager_ command prevents that behaviour on any expression. The list context is forced with a "@ operator or _list()_ command"{link: [perl 6 lookup tablet] Contextualizers}. That's not autoflattening like in Perl 5 (automatically convert a List of Lists into one List). If you still want that, "say flat(). Or say lol()"{link: [perl 6 lookup tablet] Contextualizers} to explicitly prevent autoflattening. .pre @primes = (2,3,5,7,11,13,17,19,23); # an array gets filled @primes = 2,3,5,7,11,13,17,19,23 ; # same thing, since () just do group @primes = <2 3 5 7 11 13 17 19 23>; # dito, <> is the new qw() $arrayref = 2,3,5,7,11,13,17,19,23; # in scalar context you get automatically a reference $arrayref = 13,; # comma is the new array generator @primes = 2; # array with one element @primes = [2,3,5,7,11,13,17,19,23]; # array with one element (arrayref) @dev = {'dan' => 'parrot'}; # array with one element (hashref) @data = [1..5],[6..10],[11..15]; # Array of Arrays (AoA) .pre ^^^ Array Slices .pre @primes # all values "@primes[]" # insert all values in a string, use [] as distinction from mail adresses $prime = @primes[0]; # get the first prime $prime = @primes[*-1]; # get the last one @some = @primes[2..5]; # get several $cell = @data[1][2]; # get 8, third value of second value (list) $cell = @data[1;2]; # same thing, shorten syntax @numbers = @data[1]; # get a copy of the second subarray (6..10) @copy = @data; # copy the whole AoA, no more reference passing, use binding instead .pre ^^^ Array Methods Some of the more important things you can do with lists. All the methods can also used like ops in "elems @rray;" .pre ? @rray; # boolean context, Bool::True if array has any value in it, even if its a 0 + @rray; # numeric context, number of elements (like in Perl 5 scalar @a) @rray.elems; # does the same @rray.end; # number of the last element, equal to @rray.elems-1 ~ @rray; # string context, you get content of all cells, stringified and joined @rray.cat; # does the same @rray.join(''); # also same result, you can put another string as parameter that gets between all values @rray.unshift; # prepend one value to the array @rray.shift; # remove the first value and return it @rray.push; # add one value on the end @rray.pop; # remove one value from the end and return it @rray.splice($pos,$n)# remove on $pos $n values and replace them with values that follow that two parameter @rray.delete(@ind); # delete all cell with indecies of @ind @rray.exists(@ind); # Bool::True if all indecies of @ind have a value (can be 0 or '') @rray.pick([$n]); # return $n (default is 1) randomly selected values, without duplication @rray.roll([$n]); # return $n (default is 1) randomly selected values, duplication possible (like roll dice) @rray.reverse; # all elements in reversed order @rray.rotate($n); # returns a list where $n times first item is taken to last position if $n is positive, if negative the other way around @rray.sort($coderef);# returns a sorted list by a userdefined criteria, default is alphanumerical sorting @rray.min; # numerical smallest value of that array @rray.max; # numerical largest value of that array $a,$b= @rray.minmax; # both at once, like in .sort . min or .max a sorting algorith can be provided @rray.map($coderef); # high oder map function, runs $coderef with every value as $_ and returns the list or results @rray.classify($cr); # kind of map, but creates a hash, where keys are the results of $cr and values are from @rray @rray.grep({$_>1}); # high order grep, returns only these elements that pass a condition ($cr returns something positive) @rray.first($coder); # kind of grep, return just the first matching value @rray.zip; # join arrays by picking first element left successively from here and then there .pre There is even a whole class of metaoperators that work upon lists. ^^ Hash is in Perl 6 an unordered list of Pairs. "A Pair"{link: Pair} is a single key => value association and "appears in many places"{link: [Perl 6 Language Design Tablet] Maximum reusage} of the language syntax. .pre %dev = 'pugs'=>'audreyt', 'pct'=>'pm', "STD"=>'larry'; %dev = :rakudo('jnthn'), :testsuite('moritz'); # adverb (pair) syntax works as well %dev = ('audreyt', 'pugs', 'pm', 'pct', 'larry', "STD"); # lists get autoconverted in hash context %compiler = Parrot => {Rakudo => 'jnthn'}, SMOP => {Mildew => 'ruoso'}; # hash of hashes (HoH) .pre ^^^ Hash Slices .pre my $table = %dev; # nicely formatted 2 column table using \t and \n say %dev; # only $key and $value are separated by \t ~ %dev # string context, same thing ? %dev # bool context, true if hash has any pairs + %dev # numeric context, returns number of pairs(keys) $value = %dev{'key'}; # just give me the value related to that key, like in P5 $value = %dev<pm>; # <> autoquotes like qw() in P5 $value = %dev<<$name>>; # same thing, just with eval @values = %dev{'key1', 'key2'}; @values = %dev<key1 key2>; @values = %dev<<key1 key2 $key3>>; %dev\ .{'patrick'}; # "long dot style", because its its an object in truth %dev {'audrey'}; # error, only syntax before will work %dev\ {'allison'}; # works, %dev .<dukeleto>; # error %compiler<Parrot><Rakudo>; # value in a HoH, returns 'jnthn' %compiler<SMOP>; # returns the Pair: Mildew => 'ruoso' .pre ^^^ Hash Methods .pre %dev.keys # returns the list with all keys %dev.values # list of all values %dev.kv # flat list with key1, value1, key 2 ... %dev.pairs # list of pair objects, list context default (same as in @a = %dev) %dev.invert # reverse all key => value relations .pre ^^ Callable Internally "subroutines"[Perl 6 Subroutine Tablet], "methods"[Perl 6 OOP Tablet] and alike are variables with the sigil "&" and stored in a fourth namespace. They are no more builtins with an own namespace, that can't be overwritten or augmented with your programming. ^ Object Types For a Perl beginner it's enough to know about the everywhere visible, "primary 4 variable types"{link: Primary Types}. However Perl 6 knows about "many more types"{link: [Perl 6 Lookup tablet] object types}, that are organized internally as classes or roles. You can explicitly assign one of these types to you scalar, array or hash variable. ^^ Typing ^^ Pair are very new and their syntax is used nearly everywhere in the language, where you have associations between a name and a value. .pre $pair = 'jakub' => 'helena'; # "=>" is the pair constructor $pair = :jakub('helena'); # same in adverbial notation $pair = :jakub<helena>; # same using <>, the new qw() $pair.key # returns 'jakub' $pair.value # returns 'helena' $pair.isa(Pair) # Bool::True .pre ^^ Capture also a new type, that can hold all or a part of the parameters a routine gets. Because Perl knows now positional as well as named parameters, it es some mixture of a list and array. .pre $cap = \(@a,$s,%h); # creating a capture | $cap # flatten into argument list (hash like context) || $cap # flatten into semicolon list (array like context) .pre One important difference between a compound structure of lists and hashes and a capture: while "assignments"{link: Assignment} with = the complete content of the named variables will be copied. But not so in the case of a capture. When I change $s in the last example, the content of $cap changes too, because when parameters to a routine are variables, they are also interpolated in the moment the routine is called, not when its defined. ^ Properties and Traits ^^ Properties ^^ Traits ^ Scoping "scope declarator"{link: [perl 6 lookup tablet] scope declarator}, "scopes"{link: [perl 6 lookup tablet] scopes } ^^ Twigils ^ Assignment and Binding ^^ Assignment ^^ Binding ^ Special Variables "are listed heir table"{link: [Perl 6 Lookup Tablet] special variables}. To understand their secondary sigil "look here"{link: Twigils} ---- "Overview"[Perl 6 Tablets] - _Chapter:_ "0:Intr"[Perl 6 Intro Tablet], "1:Hist"[Perl 6 History Tablet], "2:Design"[Perl 6 Language Design Tablet], *"3:Var"[Perl 6 Variable Tablet]*, "4:Op"[Perl 6 Operator Tablet], "5:IO"[Perl 6 IO Tablet], "6:{}"[Perl 6 Block Tablet], "7:Sub"[Perl 6 Subroutine Tablet], "8:OOP"[Perl 6 OOP Tablet], "9:Rx"[Perl 6 Regex Tablet] - _Appendices:_ "A:Index"[Perl 6 Index Tablet], "B:Tables"[Perl 6 Lookup Tablet], "C:Cook"[Perl 6 Cookbook Tablet], "D:Delta"[Perl 6 Delta Tablet], "E:Best of"[Best Of Perl 6 Tablet], "F:Links"[Perl 6 Links Tablet] ---- |