1# Some example and timing tests of the new hash/blocked/ordered views 2 3if [catch {package require Mk4tcl}] { 4 catch {load ./Mk4tcl.so mk4tcl} 5 catch {load ./Mk4tcl_d.dll mk4tcl} 6} 7 8proc timedRun {tag count args} { 9 set usec [lindex [time $args $count] 0] 10 if {$usec >= 1000000} { 11 set t [format {%.2f seconds} [expr {$usec/1000000.0}]] 12 } elseif {$usec >= 1000} { 13 set t [format {%.2f mSec} [expr {$usec/1000.0}]] 14 } else { 15 set t [format {%d uS} $usec] 16 } 17 puts [format { %-10s %5dx -> %s} $tag $count $t] 18 return $usec 19} 20 21proc setupPlain {} { 22 global blocked_data 23 24 file delete _large.mk 25 mk::file open db _large.mk -nocommit 26 27 if $blocked_data { 28 mk::view layout db.words {{_B {k1 k2:I v:I}}} 29 mk::view open db.words rawdata 30 catch {rename words ""} 31 rename [rawdata view blocked] words 32 } else { 33 mk::view layout db.words {k1 k2:I v:I} 34 mk::view open db.words words 35 } 36} 37 38proc teardownPlain {} { 39 teardown 40} 41 42proc setupHash {} { 43 global blocked_data blocked_map 44 45 file delete _large.mk 46 mk::file open db _large.mk -nocommit 47 48 if $blocked_data { 49 mk::view layout db.words {{_B {k1 k2:I v:I}}} 50 mk::view open db.words rawdata 51 catch {rename data ""} 52 rename [rawdata view blocked] data 53 } else { 54 mk::view layout db.words {k1 k2:I v:I} 55 mk::view open db.words data 56 } 57 58 if $blocked_map { 59 mk::view layout db.words_map {{_B {_H:I _R:I}}} 60 mk::view open db.words_map rawmap 61 #catch {rename map ""} 62 #rename [rawmap view blocked] map 63 set map [rawmap view blocked] 64 } else { 65 mk::view layout db.words_map {_H:I _R:I} 66 mk::view open db.words_map map 67 set map map 68 } 69 70 #rename [data view hash map 2] words 71 rename [data view hash $map 2] words 72} 73 74proc teardownHash {} { 75 teardown 76} 77 78proc setupOrdered {} { 79 global blocked_data 80 81 file delete _large.mk 82 mk::file open db _large.mk -nocommit 83 84 if $blocked_data { 85 mk::view layout db.words {{_B {k1 k2:I v:I}}} 86 mk::view open db.words rawdata 87 catch {rename data ""} 88 rename [rawdata view blocked] data 89 } else { 90 mk::view layout db.words {k1 k2:I v:I} 91 mk::view open db.words data 92 } 93 94 rename [data view ordered 2] words 95} 96 97proc teardownOrdered {} { 98 teardown 99} 100 101proc setupBoth {} { 102 global blocked_data blocked_map 103 104 file delete _large.mk 105 mk::file open db _large.mk -nocommit 106 107 if $blocked_data { 108 mk::view layout db.words {{_B {k1 k2:I v:I}}} 109 mk::view open db.words rawdata 110 catch {rename data ""} 111 rename [rawdata view blocked] data 112 } else { 113 mk::view layout db.words {k1 k2:I v:I} 114 mk::view open db.words data 115 } 116 117 if $blocked_map { 118 mk::view layout db.words_map {{_B {_H:I _R:I}}} 119 mk::view open db.words_map rawmap 120 #catch {rename map ""} 121 #rename [rawmap view blocked] map 122 set map [rawmap view blocked] 123 } else { 124 mk::view layout db.words_map {_H:I _R:I} 125 mk::view open db.words_map map 126 set map map 127 } 128 129 #catch {rename hash ""} 130 #rename [data view hash map 2] hash 131 set hash [data view hash $map 2] 132 133 #rename [hash view ordered 2] words 134 rename [$hash view ordered 2] words 135} 136 137proc teardownBoth {} { 138 teardown 139} 140 141proc teardown {} { 142 rename words "" 143 rename hash "" 144 rename data "" 145 rename map "" 146 147 rename rawdata "" 148 rename rawmap "" 149 150 mk::file close db 151} 152 153proc filldb {n} { 154 puts -nonewline stderr " filldb $n ... " 155 set fd [open words] 156 157 set n0 [words size] 158 set t0 [clock clicks] 159 while {[gets $fd w] >= 0} { 160 words insert end k1 $w k2 $n v [expr {$n * [string length $w]}] 161 #if {[words size] % 1000 == 0} {puts -nonewline stderr *} 162 } 163 set usec [expr {[clock clicks]-$t0}] 164 165 close $fd 166 set rps [expr {int(([words size]-$n0) / ($usec / 1000000.0))}] 167 puts stderr "$rps adds/sec ($n0..[words size] rows)" 168} 169 170proc run {type bdata bmap runs finds} { 171 global blocked_data blocked_map 172 set blocked_data $bdata 173 set blocked_map $bmap 174 175 set s "" 176 if $bdata {append s " - data is blocked"} 177 if $bmap {append s " - map is blocked"} 178 179 puts "\n*** $type$s ***\n" 180 181 proc map {args} {return ?} 182 proc rawmap {args} {return ?} 183 proc data {args} {return ?} 184 proc rawdata {args} {return ?} 185 proc hash {args} {return ?} 186 187 setup$type 188 189 set runCounter 99 190 191 while {[incr runs -1] >= 0} { 192 timedRun Fill 1 filldb [incr runCounter] 193 timedRun Commit 1 mk::file commit db 194 timedRun Find $finds words find k1 iterator k2 $runCounter 195 } 196 197 puts " [words size] rows, [map size] hash slots,\ 198 file size = [file size _large.mk]" 199 puts " [rawdata size] data blocks, [rawmap size] map blocks" 200 201 teardown$type 202} 203 204 # plain table, append at end, find with linear scan 205run Plain 0 0 3 10 206run Plain 1 0 3 10 207 208 # hash table, with data and/or map optionally blocked 209run Hash 0 0 3 1000 210run Hash 0 1 3 1000 211run Hash 1 0 3 1000 212run Hash 1 1 3 1000 213 214 # binary search, with data optionally blocked 215run Ordered 0 0 3 1000 216run Ordered 1 0 3 1000 217 218 # combination of the above: hash access, rows kept in sort order 219run Both 0 0 2 1000 220run Both 0 1 2 1000 221run Both 1 0 2 1000 222run Both 1 1 2 1000 223 224 # create larger datasets, this takes a long time 225run Plain 1 0 10 10 226run Hash 1 0 10 1000 227run Ordered 1 0 10 1000 228run Both 1 0 10 1000 229