speed1p.explain 8.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366
  1. # 2008 March 21
  2. #
  3. # The author disclaims copyright to this source code. In place of
  4. # a legal notice, here is a blessing:
  5. #
  6. # May you do good and not evil.
  7. # May you find forgiveness for yourself and forgive others.
  8. # May you share freely, never taking more than you give.
  9. #
  10. #*************************************************************************
  11. # This file implements regression tests for SQLite library. The
  12. # focus of this script is measuring executing speed.
  13. #
  14. # This is a copy of speed1.test modified to user prepared statements.
  15. #
  16. # $Id: speed1p.explain,v 1.1 2008/04/16 12:57:48 drh Exp $
  17. #
  18. set testdir [file dirname $argv0]
  19. source $testdir/tester.tcl
  20. speed_trial_init speed1
  21. # Set a uniform random seed
  22. expr srand(0)
  23. set sqlout [open speed1.txt w]
  24. proc tracesql {sql} {
  25. puts $::sqlout $sql\;
  26. }
  27. #db trace tracesql
  28. # The number_name procedure below converts its argment (an integer)
  29. # into a string which is the English-language name for that number.
  30. #
  31. # Example:
  32. #
  33. # puts [number_name 123] -> "one hundred twenty three"
  34. #
  35. set ones {zero one two three four five six seven eight nine
  36. ten eleven twelve thirteen fourteen fifteen sixteen seventeen
  37. eighteen nineteen}
  38. set tens {{} ten twenty thirty forty fifty sixty seventy eighty ninety}
  39. proc number_name {n} {
  40. if {$n>=1000} {
  41. set txt "[number_name [expr {$n/1000}]] thousand"
  42. set n [expr {$n%1000}]
  43. } else {
  44. set txt {}
  45. }
  46. if {$n>=100} {
  47. append txt " [lindex $::ones [expr {$n/100}]] hundred"
  48. set n [expr {$n%100}]
  49. }
  50. if {$n>=20} {
  51. append txt " [lindex $::tens [expr {$n/10}]]"
  52. set n [expr {$n%10}]
  53. }
  54. if {$n>0} {
  55. append txt " [lindex $::ones $n]"
  56. }
  57. set txt [string trim $txt]
  58. if {$txt==""} {set txt zero}
  59. return $txt
  60. }
  61. # Create a database schema.
  62. #
  63. do_test speed1p-1.0 {
  64. execsql {
  65. PRAGMA page_size=1024;
  66. PRAGMA cache_size=8192;
  67. PRAGMA locking_mode=EXCLUSIVE;
  68. CREATE TABLE t1(a INTEGER, b INTEGER, c TEXT);
  69. CREATE TABLE t2(a INTEGER, b INTEGER, c TEXT);
  70. CREATE INDEX i2a ON t2(a);
  71. CREATE INDEX i2b ON t2(b);
  72. }
  73. execsql {
  74. SELECT name FROM sqlite_master ORDER BY 1;
  75. }
  76. } {i2a i2b t1 t2}
  77. # 50000 INSERTs on an unindexed table
  78. #
  79. set list {}
  80. for {set i 1} {$i<=50000} {incr i} {
  81. set r [expr {int(rand()*500000)}]
  82. set x [number_name $r]
  83. lappend list $i $r $x
  84. }
  85. set script {
  86. foreach {i r x} $::list {
  87. db eval {INSERT INTO t1 VALUES($i,$r,$x)}
  88. }
  89. }
  90. explain {INSERT INTO t1 VALUES($i,$r,$x)}
  91. db eval BEGIN
  92. speed_trial_tcl speed1p-insert1 50000 row $script
  93. db eval COMMIT
  94. # 50000 INSERTs on an indexed table
  95. #
  96. set list {}
  97. for {set i 1} {$i<=50000} {incr i} {
  98. set r [expr {int(rand()*500000)}]
  99. set x [number_name $r]
  100. lappend list $i $r $x
  101. }
  102. set script {
  103. foreach {i r x} $::list {
  104. db eval {INSERT INTO t2 VALUES($i,$r,$x)}
  105. }
  106. }
  107. explain {INSERT INTO t2 VALUES($i,$r,$x)}
  108. db eval BEGIN
  109. speed_trial_tcl speed1p-insert2 50000 row $script
  110. db eval COMMIT
  111. # 50 SELECTs on an integer comparison. There is no index so
  112. # a full table scan is required.
  113. #
  114. set list {}
  115. for {set i 0} {$i<50} {incr i} {
  116. set lwr [expr {$i*100}]
  117. set upr [expr {($i+10)*100}]
  118. lappend list $lwr $upr
  119. }
  120. set script {
  121. foreach {lwr upr} $::list {
  122. db eval {SELECT count(*), avg(b) FROM t1 WHERE b>=$lwr AND b<$upr}
  123. }
  124. }
  125. explain {SELECT count(*), avg(b) FROM t1 WHERE b>=$lwr AND b<$upr}
  126. db eval BEGIN
  127. speed_trial_tcl speed1p-select1 [expr {50*50000}] row $script
  128. db eval COMMIT
  129. # 50 SELECTs on an LIKE comparison. There is no index so a full
  130. # table scan is required.
  131. #
  132. set list {}
  133. for {set i 0} {$i<50} {incr i} {
  134. lappend list "%[number_name $i]%"
  135. }
  136. set script {
  137. foreach pattern $::list {
  138. db eval {SELECT count(*), avg(b) FROM t1 WHERE c LIKE $pattern}
  139. }
  140. }
  141. explain {SELECT count(*), avg(b) FROM t1 WHERE c LIKE $pattern}
  142. db eval BEGIN
  143. speed_trial_tcl speed1p-select2 [expr {50*50000}] row $script
  144. db eval COMMIT
  145. # Create indices
  146. #
  147. explain {CREATE INDEX i1a ON t1(a)}
  148. explain {CREATE INDEX i1b ON t1(b)}
  149. db eval BEGIN
  150. speed_trial speed1p-createidx 150000 row {
  151. CREATE INDEX i1a ON t1(a);
  152. CREATE INDEX i1b ON t1(b);
  153. CREATE INDEX i1c ON t1(c);
  154. }
  155. db eval COMMIT
  156. # 5000 SELECTs on an integer comparison where the integer is
  157. # indexed.
  158. #
  159. set list {}
  160. for {set i 0} {$i<5000} {incr i} {
  161. set lwr [expr {$i*100}]
  162. set upr [expr {($i+10)*100}]
  163. lappend list $lwr $upr
  164. }
  165. set script {
  166. foreach {lwr upr} $::list {
  167. db eval {SELECT count(*), avg(b) FROM t1 WHERE b>=$lwr AND b<$upr}
  168. }
  169. }
  170. explain {SELECT count(*), avg(b) FROM t1 WHERE b>=$lwr AND b<$upr}
  171. db eval BEGIN
  172. speed_trial_tcl speed1p-select3 5000 stmt $script
  173. db eval COMMIT
  174. # 100000 random SELECTs against rowid.
  175. #
  176. set list {}
  177. for {set i 1} {$i<=100000} {incr i} {
  178. set id [expr {int(rand()*50000)+1}]
  179. lappend list $id
  180. }
  181. set script {
  182. foreach id $::list {
  183. db eval {SELECT c FROM t1 WHERE rowid=$id}
  184. }
  185. }
  186. explain {SELECT c FROM t1 WHERE rowid=$id}
  187. db eval BEGIN
  188. speed_trial_tcl speed1p-select4 100000 row $script
  189. db eval COMMIT
  190. # 100000 random SELECTs against a unique indexed column.
  191. #
  192. set list {}
  193. for {set i 1} {$i<=100000} {incr i} {
  194. set id [expr {int(rand()*50000)+1}]
  195. lappend list $id
  196. }
  197. set script {
  198. foreach id $::list {
  199. db eval {SELECT c FROM t1 WHERE a=$id}
  200. }
  201. }
  202. explain {SELECT c FROM t1 WHERE a=$id}
  203. db eval BEGIN
  204. speed_trial_tcl speed1p-select5 100000 row $script
  205. db eval COMMIT
  206. # 50000 random SELECTs against an indexed column text column
  207. #
  208. set list [db eval {SELECT c FROM t1 ORDER BY random() LIMIT 50000}]
  209. set script {
  210. foreach c $::list {
  211. db eval {SELECT c FROM t1 WHERE c=$c}
  212. }
  213. }
  214. explain {SELECT c FROM t1 WHERE c=$c}
  215. db eval BEGIN
  216. speed_trial_tcl speed1p-select6 50000 row $script
  217. db eval COMMIT
  218. # Vacuum
  219. speed_trial speed1p-vacuum 100000 row VACUUM
  220. # 5000 updates of ranges where the field being compared is indexed.
  221. #
  222. set list {}
  223. for {set i 0} {$i<5000} {incr i} {
  224. set lwr [expr {$i*2}]
  225. set upr [expr {($i+1)*2}]
  226. lappend list $lwr $upr
  227. }
  228. set script {
  229. foreach {lwr upr} $::list {
  230. db eval {UPDATE t1 SET b=b*2 WHERE a>=$lwr AND a<$upr}
  231. }
  232. }
  233. explain {UPDATE t1 SET b=b*2 WHERE a>=$lwr AND a<$upr}
  234. db eval BEGIN
  235. speed_trial_tcl speed1p-update1 5000 stmt $script
  236. db eval COMMIT
  237. # 50000 single-row updates. An index is used to find the row quickly.
  238. #
  239. set list {}
  240. for {set i 0} {$i<50000} {incr i} {
  241. set r [expr {int(rand()*500000)}]
  242. lappend list $i $r
  243. }
  244. set script {
  245. foreach {i r} $::list {
  246. db eval {UPDATE t1 SET b=$r WHERE a=$i}
  247. }
  248. }
  249. explain {UPDATE t1 SET b=$r WHERE a=$i}
  250. db eval BEGIN
  251. speed_trial_tcl speed1p-update2 50000 row $script
  252. db eval COMMIT
  253. # 1 big text update that touches every row in the table.
  254. #
  255. explain {UPDATE t1 SET c=a}
  256. speed_trial speed1p-update3 50000 row {
  257. UPDATE t1 SET c=a;
  258. }
  259. # Many individual text updates. Each row in the table is
  260. # touched through an index.
  261. #
  262. set list {}
  263. for {set i 1} {$i<=50000} {incr i} {
  264. set r [expr {int(rand()*500000)}]
  265. lappend list $i [number_name $r]
  266. }
  267. set script {
  268. foreach {i x} $::list {
  269. db eval {UPDATE t1 SET c=$x WHERE a=$i}
  270. }
  271. }
  272. explain {UPDATE t1 SET c=$x WHERE a=$i}
  273. db eval BEGIN
  274. speed_trial_tcl speed1p-update4 50000 row $script
  275. db eval COMMIT
  276. # Delete all content in a table.
  277. #
  278. explain {DELETE FROM t1}
  279. speed_trial speed1p-delete1 50000 row {DELETE FROM t1}
  280. # Copy one table into another
  281. #
  282. explain {INSERT INTO t1 SELECT * FROM t2}
  283. speed_trial speed1p-copy1 50000 row {INSERT INTO t1 SELECT * FROM t2}
  284. # Delete all content in a table, one row at a time.
  285. #
  286. explain {DELETE FROM t1 WHERE 1}
  287. speed_trial speed1p-delete2 50000 row {DELETE FROM t1 WHERE 1}
  288. # Refill the table yet again
  289. #
  290. speed_trial speed1p-copy2 50000 row {INSERT INTO t1 SELECT * FROM t2}
  291. # Drop the table and recreate it without its indices.
  292. #
  293. explain {DROP TABLE t1}
  294. explain {CREATE TABLE tX(a INTEGER, b INTEGER, c TEXT)}
  295. db eval BEGIN
  296. speed_trial speed1p-drop1 50000 row {
  297. DROP TABLE t1;
  298. CREATE TABLE t1(a INTEGER, b INTEGER, c TEXT);
  299. }
  300. db eval COMMIT
  301. # Refill the table yet again. This copy should be faster because
  302. # there are no indices to deal with.
  303. #
  304. speed_trial speed1p-copy3 50000 row {INSERT INTO t1 SELECT * FROM t2}
  305. # Select 20000 rows from the table at random.
  306. #
  307. explain {SELECT rowid FROM t1 ORDER BY random() LIMIT 20000}
  308. speed_trial speed1p-random1 50000 row {
  309. SELECT rowid FROM t1 ORDER BY random() LIMIT 20000
  310. }
  311. # Delete 20000 random rows from the table.
  312. #
  313. explain {DELETE FROM t1 WHERE rowid IN
  314. (SELECT rowid FROM t1 ORDER BY random() LIMIT 20000)}
  315. speed_trial speed1p-random-del1 20000 row {
  316. DELETE FROM t1 WHERE rowid IN
  317. (SELECT rowid FROM t1 ORDER BY random() LIMIT 20000)
  318. }
  319. do_test speed1p-1.1 {
  320. db one {SELECT count(*) FROM t1}
  321. } 30000
  322. # Delete 20000 more rows at random from the table.
  323. #
  324. speed_trial speed1p-random-del2 20000 row {
  325. DELETE FROM t1 WHERE rowid IN
  326. (SELECT rowid FROM t1 ORDER BY random() LIMIT 20000)
  327. }
  328. do_test speed1p-1.2 {
  329. db one {SELECT count(*) FROM t1}
  330. } 10000
  331. speed_trial_summary speed1
  332. finish_test