Rules / Types, classes & roles / composite

Bag Reference

Immutable collection of distinct objects with integer weights

What it is #

Routines #

Signatures are reproduced from the documentation, including their declared return types. A routine listed here is part of the type's published interface; whether Raku++ implements it is a separate question, answered by the examples below.

sub bag #

sub bag(*@args --> Bag)

Returns Bag.

Creates a new Bag from @args. This method is inherited from Any, however, Mixes do not have an inherent order and you should not trust it returning a consistent output. Sets, Bags, and Mixes

Examples, run three ways #

Every example below comes from the official documentation, together with the output that documentation asserts. Each was then executed by Rakudo and by Raku++ when this page was built. Where the three agree, one result is shown; where they do not, all three are — because which of them is wrong is exactly the information worth having.

1 all-differ · 4 doc-drift · 5 no-output · 2 ok · 1 rakudo-differs

class Bag does Baggy { }

Not executed: the documentation states no expected output for this example.

my $breakfast = bag <spam eggs spam spam bacon spam>;

say $breakfast.elems;      # OUTPUT: «3␤»
say $breakfast.keys.sort;  # OUTPUT: «bacon eggs spam␤»

say $breakfast.total;      # OUTPUT: «6␤»
say $breakfast.kxxv.sort;  # OUTPUT: «bacon eggs spam spam spam spam␤»
Documentation
3
bacon eggs spam
6
bacon eggs spam spam spam spam
Rakudo
3
(bacon eggs spam)
6
(bacon eggs spam spam spam spam)
Raku++
3
(bacon eggs spam)
6
(bacon eggs spam spam spam spam)

Both engines agree; the documentation states something else. Trust the engines.

my $breakfast = bag <spam eggs spam spam bacon spam>;
say $breakfast<bacon>;    # OUTPUT: «1␤»
say $breakfast<spam>;     # OUTPUT: «4␤»
say $breakfast<sausage>;  # OUTPUT: «0␤»
Output
1
4
0

Documentation, Rakudo and Raku++ all agree.

my $n = bag "a" => 0, "b" => 1, "c" => 2, "c" => 2;
say $n.keys.raku;        # OUTPUT: «(:c(2), :b(1), :a(0)).Seq␤»
say $n.keys.map(&WHAT);  # OUTPUT: «((Pair) (Pair) (Pair))␤»
say $n.values.raku;      # OUTPUT: «(2, 1, 1).Seq␤»
Documentation
(:c(2), :b(1), :a(0)).Seq
((Pair) (Pair) (Pair))
(2, 1, 1).Seq
Rakudo
(:c(2), :a(0), :b(1)).Seq
((Pair) (Pair) (Pair))
(2, 1, 1).Seq
Raku++
(:a(0), :b(1), :c(2)).Seq
((Pair) (Pair) (Pair))
(1, 1, 2).Seq

All three differ. Needs a human.

Not yet examined. Which of these is correct has not been established — do not treat either engine as settled here.

my $n = ("a" => 0, "b" => 1, "c" => 2, "c" => 2).Bag;
say $n.keys.raku;        # OUTPUT: «("b", "c").Seq␤»
say $n.keys.map(&WHAT);  # OUTPUT: «((Str) (Str))␤»
say $n.values.raku;      # OUTPUT: «(1, 4).Seq␤»
Documentation
("b", "c").Seq
((Str) (Str))
(1, 4).Seq
Rakudo
("c", "b").Seq
((Str) (Str))
(4, 1).Seq
Raku++
("b", "c").Seq
((Str) (Str))
(1, 4).Seq

Raku++ matches the documentation; Rakudo does not. This is the one class where neither engine can be assumed right: it may be a stale doc that Raku++ was built from, or it may be a Rakudo bug that the documentation predates. Each case is examined individually.

Not yet examined. Which of these is correct has not been established — do not treat either engine as settled here.

say (1..5) (+) 4;  # OUTPUT: «Bag(1 2 3 4(2) 5)␤»
Output
Bag(1 2 3 4(2) 5)

Documentation, Rakudo and Raku++ all agree.

my $breakfast = Bag.new( <spam eggs spam spam bacon spam> );

Not executed: the documentation states no expected output for this example.

# only allow strings (Str) in the Bag
my $breakfast = Bag[Str].new( <spam eggs spam spam bacon spam> );

Not executed: the documentation states no expected output for this example.

# only allow whole numbers (Int) in the Bag
my $breakfast = Bag[Int].new( <spam eggs spam spam bacon spam> );
# Type check failed in binding; expected Int but got Str ("spam")

Not executed: the documentation states no expected output for this example.

my %b is Bag = <a b c>;
say %b<a>;  # OUTPUT: «True␤»
say %b<d>;  # OUTPUT: «False␤»
Documentation
True
False
Rakudo
1
0
Raku++
1
0

Both engines agree; the documentation states something else. Trust the engines.

# limit to strings
my %b is Bag[Str] = <a b c>;
say %b<a>;  # OUTPUT: «True␤»
say %b<d>;  # OUTPUT: «False␤»
Documentation
True
False
Rakudo
1
0
Raku++
1
0

Both engines agree; the documentation states something else. Trust the engines.

# limit to whole numbers
my %b is Bag[Int] = <a b c>;
# Type check failed in binding; expected Int but got Str ("a")

Not executed: the documentation states no expected output for this example.

my ($a, $b) = bag(2, 2, 4), bag(2, 3, 3, 4);

say $a (<) $b;   # OUTPUT: «False␤»
say $a (<=) $b;  # OUTPUT: «False␤»
say $a (^) $b;   # OUTPUT: «Bag(3(2) 2)␤»
say $a (+) $b;   # OUTPUT: «Bag(2(3) 4(2) 3(2))␤»

# Unicode versions:
say $a ⊂ $b;  # OUTPUT: «False␤»
say $a ⊆ $b;  # OUTPUT: «False␤»
say $a ⊖ $b;  # OUTPUT: «Bag(3(2) 2)␤»
say $a ⊎ $b;  # OUTPUT: «Bag(2(3) 4(2) 3(2))␤»
Documentation
False
False
Bag(3(2) 2)
Bag(2(3) 4(2) 3(2))
False
False
Bag(3(2) 2)
Bag(2(3) 4(2) 3(2))
Rakudo
False
False
Bag(2 3(2))
Bag(2(3) 3(2) 4(2))
False
False
Bag(2 3(2))
Bag(2(3) 3(2) 4(2))
Raku++
False
False
Bag(2 3(2))
Bag(2(3) 3(2) 4(2))
False
False
Bag(2 3(2))
Bag(2(3) 3(2) 4(2))

Both engines agree; the documentation states something else. Trust the engines.