Subject: | funny behavior in Set::Scalar::Base::intersection and Set::Scalar::Base::union |
Hi,
I took a more careful look for any bugs that my fix for bug 13816 might have introduced.
I noticed the following at line 296 of Set::Scalar::Base::intersection:
$intersection = $self
if $intersection->size == $self->size;
This seems like a good idea, it allocates memory more efficiently for big sets. However, I propose that this introduces unwanted behavior. Here's an example:
==================
use Set::Scalar ;
use Scalar::Util qw/refaddr/ ;
my $x = new Set::Scalar(1,2,3) ;
my $y = new Set::Scalar(1,2,3,5);
my $i = $x->intersection($y) ;
printf('Address of $x: %x' . "\n", refaddr $x) ;
printf('Address of $y: %x' . "\n", refaddr $y) ;
printf('Address of $i: %x' . "\n", refaddr $i) ;
print "\n" ;
$i->insert(4) ;
print '$x is the set: ' , $x , "\n" ;
print '$y is the set: ' , $y , "\n" ;
print '$i is the set: ' , $i , "\n" ;
==================
And the output...
==================
Address of $x: 8194a44
Address of $y: 8194a50
Address of $i: 8194a44
$x is the set: (1 2 3 4)
$y is the set: (1 2 3 5)
$i is the set: (1 2 3 4)
==================
You'll notice that $x and $i both have the same address after the intersection. Further, you'll notice that this causes ALL modifications to $i or $x to be reflected in both. Thus, both $x and $i have the extra element "4" even though it has only been added to $i.
Proposed fix? Ensure that intersection always returns a new object by eliminating the above mentioned line.
The same behavior is present in Set::Scalar::Base::union (line 241)
Thanks,
Josh