Mr. Shawn H. Corey wrote: > Your solution will only work if $element is unique. Otherwise you will > have multiple copies of $element on the list, and not the $maximum > (unique) number of items. > > Try: > > @recent = grep { ! /^$element$/ } @recent; > unshift @recent, $element; > $#recent = $maximum; > > Notice how things became even slower? > >
OK, here's a solution that might be faster. The problem with it is as_array() which has to scan the list every time. There is not simpler way for it to work. #!/usr/bin/perl use strict; use warnings; my $maximum = 20; # minimum maximum == 2 my $head = 0; my $tail = 0; my %unique = (); my $count = 0; sub add_element { my $element = shift @_; my $node = { next => 0, back => 0, data => $element, }; if( exists $unique{$element} ){ if( $unique{$element} eq $head ){ $head = $unique{$element}->{next}; }else{ $unique{$element}->{back}->{next} = $unique{$element}->{next}; } if( $unique{$element} eq $tail ){ $tail = $unique{$element}->{back}; }else{ $unique{$element}->{next}->{back} = $unique{$element}->{back}; } } if( ref( $head )){ $node->{next} = $head; $head->{back} = $node; }else{ $tail = $node; } $head = $node; $unique{$element} = $node; $count ++; if( $count > $maximum ){ my $item = $tail->{data}; $tail = $tail->{back}; $tail->{next} = 0; delete $unique{$item}; } } sub as_array { my @array = (); my $node = $head; while( ref( $node )){ push @array, $node->{data}; $node = $node->{next}; } return @array; } for my $n ( qw( a b c b a a b c d e f g h i j k l m n o p q r s t u v w x y z ) ){ add_element( $n ); print join( " ", as_array ), "\n"; } -- __END__ Just my 0.00000002 million dollars worth, --- Shawn "For the things we have to learn before we can do them, we learn by doing them." Aristotle * Perl tutorials at http://perlmonks.org/?node=Tutorials * A searchable perldoc is at http://perldoc.perl.org/ -- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] <http://learn.perl.org/> <http://learn.perl.org/first-response>