| 117 | | |
| | 117 | =item Ordering |
| | 118 | |
| | 119 | subset KeyExtractor of Code where { .sig === :(Any --> Any) }; |
| | 120 | subset Comparator of Code where { .sig === :(Any, Any --> Int ) }; |
| | 121 | subset OrderingPair of Pair where { .left ~~ KeyExtractor && .right ~~ Comparator }; |
| | 122 | |
| | 123 | subset Ordering where Signature | KeyExtractor | Comparator | OrderingPair; |
| | 124 | |
| | 125 | Used to handle comparisons between things. Generally this |
| | 126 | ends up in functions like C<cmp()>, C<eqv()>, C<sort()>, |
| | 127 | C<min()>, C<max()>, etc., as a $by parameter which provides |
| | 128 | the information on how two things compare relative to each other. |
| | 129 | |
| | 130 | Note that C<eqv()> and C<cmp()> do almost but not the same thing |
| | 131 | since with C<eqv()> you don't care if two things are ordered |
| | 132 | increasing or decreasing but only if they are the same or not. |
| | 133 | Rather than declare an C<Equiving> type declaration C<Ordering> will |
| | 134 | just do double duty. |
| | 135 | |
| | 136 | =over |
| | 137 | |
| | 138 | =item Comparator |
| | 139 | |
| | 140 | A closure with arity of 2, which for ordering returns |
| | 141 | negative/zero/positive, signaling the first argument should |
| | 142 | be before/tied with/after the second. aka "The Perl 5 way". |
| | 143 | |
| | 144 | For equivalence the closure returns either not 0 or 0 indicating |
| | 145 | if the first argument is equivalent or not to the second. |
| | 146 | |
| | 147 | =item KeyExtractor |
| | 148 | |
| | 149 | A closure with arity of 1, which returns the "key" by which |
| | 150 | to compare. Values are compared using C<cmp> for orderings |
| | 151 | and C<eqv> for equivalences, which in Perl 6 do different |
| | 152 | comparisons depending on the types. (To get a Perl 5 string |
| | 153 | ordering you must compare with C<leg> instead.) |
| | 154 | |
| | 155 | Internally the result of the KeyExtractor on a value should |
| | 156 | be cached. |
| | 157 | |
| | 158 | =item OrderingPair |
| | 159 | |
| | 160 | A combination of the two methods above, for when one wishes |
| | 161 | to take advantage of the internal caching of keys that is |
| | 162 | expected to happen, but wishes to compare them with something |
| | 163 | other than C<eqv> or C<cmp>, such as C<E<lt>=E<gt>> or C<leg>. |
| | 164 | |
| | 165 | =item Signature |
| | 166 | |
| | 167 | If a signature is specified as a criterion, the signature is |
| | 168 | bound to each value and then each parameter does comparisons |
| | 169 | in positional order according to its type, as modified by |
| | 170 | its traits. Basically, the system will write the body of |
| | 171 | the key extraction and comparison subroutine for you based on |
| | 172 | the signature. |
| | 173 | |
| | 174 | For ordering the list of positional parameter comparisons is |
| | 175 | reduced as if using [||] but all comparisons do not need to be |
| | 176 | performed if an early one determines an increasing or decreasing |
| | 177 | order. For equivalence the list is reduced as if using [&&]. |
| | 182 | |
| | 183 | =head2 Any |
| | 184 | |
| | 185 | The following are defined in the C<Any> role: |
| | 186 | |
| | 187 | =over |
| | 188 | |
| | 189 | =item eqv |
| | 190 | |
| | 191 | our Bool multi sub eqv (Ordering @by, $a, $b); |
| | 192 | our Bool multi sub eqv (Ordering $by = &infix:<eqv>, $a, $b); |
| | 193 | |
| | 194 | Returns a Bool indicating if the parameters are equivalent, |
| | 195 | using criteria C<$by> or C<@by> for comparisons. C<@by> differs |
| | 196 | from C<$by> in that each criterion is applied, in order, |
| | 197 | until a non-zero (equivalent) result is achieved. |
| | 198 | |
| | 199 | =item cmp |
| | 200 | |
| | 201 | our Order multi sub cmp (Ordering @by, $a, $b); |
| | 202 | our Order multi sub cmp (Ordering $by = &infix:<cmp>, $a, $b); |
| | 203 | |
| | 204 | Returns Order::Increase, Order::Decrease, or Order::Same |
| | 205 | (which numify to -1, 0, +1) indicating if paramater $a should |
| | 206 | be ordered before/tied with/after parameter $b, using criteria |
| | 207 | C<$by> or C<@by> for comparisons. C<@by> differs from C<$by> |
| | 208 | in that each criterion is applied, in order, until a non-zero |
| | 209 | (tie) result is achieved. |
| 612 | | our Lazy multi method pick ( @values: Int $num = 1 ) |
| 613 | | our Lazy multi method pick ( @values: Whatever ) |
| 614 | | our Lazy multi pick ( Int $num, *@values ) |
| 615 | | our Lazy multi pick ( Whatever, *@values ) |
| 616 | | |
| 617 | | C<pick> takes a list or array of values and returns a random selection |
| 618 | | of elements from the list (without replacement). If C<*> is specified |
| 619 | | as the number (or if the number of elements in the list is less than |
| 620 | | the specified number), all the available elements are returned in |
| 621 | | random order: |
| | 698 | our Lazy multi method pick ( @values: Int $num = 1, Bool :$repl ) |
| | 699 | our Lazy multi method pick ( @values: Whatever , Bool :$repl ) |
| | 700 | our Lazy multi pick ( Int $num, *@values , Bool :$repl ) |
| | 701 | our Lazy multi pick ( Whatever, *@values , Bool :$repl ) |
| | 702 | |
| | 703 | C<pick> takes a list or array of values and returns a random |
| | 704 | selection of elements from the list (without replacement unless |
| | 705 | :repl is indicated). When selecting without replacement if C<*> |
| | 706 | is specified as the number (or if the number of elements in |
| | 707 | the list is less than the specified number), all the available |
| | 708 | elements are returned in random order: |
| 705 | | our Array multi method sort( @values: SortCriterion @by ) |
| 706 | | our Array multi method sort( @values: SortCriterion $by = &infix:<cmp> ) |
| 707 | | |
| 708 | | our List multi sort( SortCriterion @by, *@values ) |
| 709 | | our List multi sort( SortCriterion $by = &infix:<cmp>, *@values ) |
| | 794 | our Array multi method sort( @values: Ordering @by ) |
| | 795 | our Array multi method sort( @values: Ordering $by = &infix:<cmp> ) |
| | 796 | |
| | 797 | our List multi sort( Ordering @by, *@values ) |
| | 798 | our List multi sort( Ordering $by = &infix:<cmp>, *@values ) |
| 715 | | Criteria can take a few different forms: |
| 716 | | |
| 717 | | =over 8 |
| 718 | | |
| 719 | | =item Comparator |
| 720 | | |
| 721 | | A closure with arity of 2, which returns negative/zero/positive, |
| 722 | | signaling the first argument should be before/tied with/after the |
| 723 | | second in the final ordering of the List. aka "The Perl 5 way" |
| 724 | | |
| 725 | | =item KeyExtractor |
| 726 | | |
| 727 | | A closure with arity of 1, which returns the "key" by which to sort. |
| 728 | | Values are compared using C<cmp>, which in Perl 6 does different |
| 729 | | comparisons depending on the types. (To get a Perl 5 string comparison |
| 730 | | you must use C<leg> instead.) |
| 731 | | |
| 732 | | =item Pair(KeyExtractor, Comparator) |
| 733 | | |
| 734 | | A combination of the two methods above, for when one wishes to take |
| 735 | | advantage of the internal caching of keys that is expected to happen, |
| 736 | | but wishes to compare them with something other than C<cmp>, such |
| 737 | | as C<E<lt>=E<gt>> or C<leg>. |
| 738 | | |
| 739 | | =item Signature |
| 740 | | |
| 741 | | If a signature is specified as a criterion, the signature is bound |
| 742 | | to each value and then each parameter does comparisons in positional order |
| 743 | | according to its type, as modified by its traits. Sort-specific traits |
| 744 | | are allowed in such a signature such as C<is descending> or C<is insensitive>. |
| 745 | | Basically, the system will write the body of the key extraction subroutine |
| 746 | | for you based on the signature. |
| 747 | | |
| 748 | | =back |
| 749 | | |
| 750 | | Any Criterion may receive either or both of the mixins C<descending> |
| 751 | | and C<insensitive> to reverse the order of sort, or the adjust the |
| 752 | | case sensitivity of C<cmp> as a Comparator. (Mixins are applied to |
| 753 | | values using C<but>.) |
| | 804 | C<Ordering> is as described in L<"Type Declarations">. Any |
| | 805 | C<Ordering> may receive either or both of the mixins C<descending> |
| | 806 | and C<canonicalized(Code $how)> to reverse the order of sort, or |
| | 807 | to adjust the case, sign, or other order sensitivity of C<cmp>. |
| | 808 | (Mixins are applied to values using C<but>.) If a C<Signature> |
| | 809 | is used as an C<Ordering> then sort-specific traits such as C<is |
| | 810 | canonicalized($how)> are allowed on the positional elements. |
| 760 | | See L<http://www.nntp.perl.org/group/perl.perl6.language/16578> for more |
| 761 | | details and examples. |
| 762 | | |
| 763 | | |
| | 817 | See L<http://www.nntp.perl.org/group/perl.perl6.language/16578> |
| | 818 | for more details and examples (with C<is insensitive> meaning |
| | 819 | C<is canonicalized(&lc)>.) |
| | 820 | |
| | 821 | =item min |
| | 822 | |
| | 823 | our Array multi method min( @values: *&by ) |
| | 824 | our Array multi method min( @values: Ordering @by ) |
| | 825 | our Array multi method min( @values: Ordering $by = &infix:<cmp> ) |
| | 826 | |
| | 827 | our List multi min( Ordering @by, *@values ) |
| | 828 | our List multi min( Ordering $by = &infix:<cmp>, *@values ) |
| | 829 | |
| | 830 | Returns the earliest (i.e., lowest index) minimum element |
| | 831 | of C<@values> , using criteria C<$by> or C<@by> for |
| | 832 | comparisons. C<@by> differs from C<$by> in that each criterion |
| | 833 | is applied, in order, until a non-zero (tie) result is achieved. |
| | 834 | |
| | 835 | C<Ordering> is as described in L<"Type Declarations">. Any |
| | 836 | C<Ordering> may receive the mixin C<canonicalized(Code $how)> to |
| | 837 | adjust the case, sign, or other order sensitivity of C<cmp>. |
| | 838 | (Mixins are applied to values using C<but>.) If a C<Signature> |
| | 839 | is used as an C<Ordering> then sort-specific traits such as C<is |
| | 840 | canonicalized($how)> are allowed on the positional elements. |
| | 841 | |
| | 842 | =item max |
| | 843 | |
| | 844 | our Array multi method max( @values: *&by ) |
| | 845 | our Array multi method max( @values: Ordering @by ) |
| | 846 | our Array multi method max( @values: Ordering $by = &infix:<cmp> ) |
| | 847 | |
| | 848 | our List multi max( Ordering @by, *@values ) |
| | 849 | our List multi max( Ordering $by = &infix:<cmp>, *@values ) |
| | 850 | |
| | 851 | Returns the earliest (i.e., lowest index) maximum element |
| | 852 | of C<@values> , using criteria C<$by> or C<@by> for |
| | 853 | comparisons. C<@by> differs from C<$by> in that each criterion |
| | 854 | is applied, in order, until a non-zero (tie) result is achieved. |
| | 855 | |
| | 856 | C<Ordering> is as described in L<"Type Declarations">. Any |
| | 857 | C<Ordering> may receive the mixin C<canonicalized(Code $how)> to |
| | 858 | adjust the case, sign, or other order sensitivity of C<cmp>. |
| | 859 | (Mixins are applied to values using C<but>.) If a C<Signature> |
| | 860 | is used as an C<Ordering> then sort-specific traits such as C<is |
| | 861 | canonicalized($how)> are allowed on the positional elements. |