- (RT #51888) Applied POD patch (Thanks, FWIE!)
- (RT #44981) Added VERSION to ::Array, ::Engine, and ::Hash
- Removed extraneous slashes from POD links (Thanks ilmari!)
+ - (RT #50541) Fixed bug in clear() for hashes in the File backend.
+ - This has caused a regression in speed for clear() when clearing
+ large hashes using running with the File backend. ->clear() (on my
+ machine) now takes ( N / 40 ) ** (1.66) seconds. So, clearing 4000
+ keys (as is the test in t/03_bighash.t) would take ~2070 seconds.
1.0019_001 Dec 31 22:00:00 2009 EST
(This is the first developer release for 1.0020.)
$self->lock_exclusive;
- #XXX Rewrite this dreck to do it in the engine as a tight loop vs.
- # iterating over keys - such a WASTE - is this required for transactional
- # clearning?! Surely that can be detected in the engine ...
- if ( $self->_type eq TYPE_HASH ) {
- my $key = $self->first_key;
- while ( $key ) {
- # Retrieve the key before deleting because we depend on next_key
- my $next_key = $self->next_key( $key );
- $self->_engine->delete_key( $self, $key, $key );
- $key = $next_key;
- }
- }
- else {
- my $size = $self->FETCHSIZE;
- for my $key ( 0 .. $size - 1 ) {
- $self->_engine->delete_key( $self, $key, $key );
- }
- $self->STORESIZE( 0 );
- }
+ # Dispatch to the specific clearing functionality.
+ $self->_clear;
$self->unlock;
return 1;
}
+sub _clear {
+ my $self = shift;
+
+ my $size = $self->FETCHSIZE;
+ for my $key ( 0 .. $size - 1 ) {
+ $self->_engine->delete_key( $self, $key, $key );
+ }
+ $self->STORESIZE( 0 );
+
+ return;
+}
+
sub length { (shift)->FETCHSIZE(@_) }
sub pop { (shift)->POP(@_) }
sub push { (shift)->PUSH(@_) }
sub first_key { (shift)->FIRSTKEY(@_) }
sub next_key { (shift)->NEXTKEY(@_) }
+sub _clear {
+ my $self = shift;
+
+ while ( my $key = $self->first_key ) {
+ $self->_engine->delete_key( $self, $key, $key );
+ }
+
+ return;
+}
+
sub _copy_node {
my $self = shift;
my ($db_temp) = @_;
$sector->find_md5( $args->{key_md5} );
# See whether or not we need to reindex the bucketlist
- # Yes, the double-braces are there for a reason. if() doesn't create a redo-able block,
- # so we have to create a bare block within the if() for redo-purposes. Patch and idea
- # submitted by sprout@cpan.org. -RobK, 2008-01-09
+ # Yes, the double-braces are there for a reason. if() doesn't create a
+ # redo-able block, so we have to create a bare block within the if() for
+ # redo-purposes.
+ # Patch and idea submitted by sprout@cpan.org. -RobK, 2008-01-09
if ( !$sector->has_md5 && $args->{create} && $sector->{idx} == -1 ) {{
my $redo;
} qr/Cannot use an undefined hash key/, "EXISTS fails on an undefined key";
}
+{
+ # RT# 50541 (reported by Peter Scott)
+ # clear() leaves one key unless there's only one
+ my $dbm_factory = new_dbm();
+ while ( my $dbm_maker = $dbm_factory->() ) {
+ my $db = $dbm_maker->();
+
+ $db->{block} = { };
+ $db->{critical} = { };
+ $db->{minor} = { };
+
+ cmp_ok( scalar(keys( %$db )), '==', 3, "Have 3 keys" );
+
+ $db->clear;
+
+ cmp_ok( scalar(keys( %$db )), '==', 0, "clear clears everything" );
+ }
+}
+
done_testing;
if ( $ENV{TEST_MYSQL_DSN} ) {
push @reset_funcs, sub {
+ require 'DBI.pm';
my $dbh = DBI->connect(
$ENV{TEST_MYSQL_DSN},
$ENV{TEST_MYSQL_USER},