I upgraded to 3.7.1.1 and tested this...glob works wonderfully...especially 
when there are few hits it makes a huge difference since it uses the index.

I don't see why like shouldn't be using the index in these cases as that's what 
the docs appear to say it should do.  A%A meets the qualifications for it.

I had a dictionary of 1M word phrases I used.



sqlite> pragma cache_size=200000;
sqlite> .separator ','
sqlite> create table words(id integer,word text);
sqlite> .import 1000000.dat words
sqlite> create index idx on words(word);
sqlite> .timer on
sqlite> select count(*) from words where word glob 'P*P';
4241
CPU Time: user 0.250000 sys 0.000000

sqlite> select count(*) from words where word like 'P%P';
4241
CPU Time: user 0.328125 sys 0.000000

sqlite> select count(*) from words where word like 'A%A';
0
CPU Time: user 0.281250 sys 0.000000

sqlite> select count(*) from words where word like 'Z%Z';
0
CPU Time: user 0.281250 sys 0.000000

sqlite> select count(*) from words where word glob 'Z*Z';
0
CPU Time: user 0.000000 sys 0.000000

sqlite> select count(*) from words where word glob 'L*P';
136
CPU Time: user 0.015625 sys 0.000000

sqlite> select count(*) from words where word like 'L%P';
136
CPU Time: user 0.281250 sys 0.000000



Michael D. Black

Senior Scientist

NG Information Systems

Advanced Analytics Directorate



________________________________
From: sqlite-users-boun...@sqlite.org [sqlite-users-boun...@sqlite.org] on 
behalf of Black, Michael (IS) [michael.bla...@ngc.com]
Sent: Sunday, July 10, 2011 12:03 PM
To: General Discussion of SQLite Database
Subject: EXT :Re: [sqlite] using index when using concatination

3.7.4 doesn't indicate it will use an index in either case with like...but glob 
seems to call the index...why does glob use the index but like does not?





sqlite> create table words(word text);
sqlite> create index idx on words(word);
sqlite> explain query plan select * from words where "word" like 'a' || '%' || 
'a';
sele  order          from  deta
----  -------------  ----  ----
0     0              0     SCAN TABLE words (~500000 rows)
sqlite> explain query plan select * from words where word like 'a%a';
sele  order          from  deta
----  -------------  ----  ----
0     0              0     SCAN TABLE words (~500000 rows)
sqlite> explain query plan select * from words where word like 'a%';
sele  order          from  deta
----  -------------  ----  ----
0     0              0     SCAN TABLE words (~500000 rows)
sqlite> explain query plan select * from words where word glob 'a%';
sele  order          from  deta
----  -------------  ----  ----
0     0              0     SEARCH TABLE words USING COVERING INDEX idx (word>? 
AND word<?) (~55000 rows)
sqlite> explain query plan select * from words where word glob 'a%b';
sele  order          from  deta
----  -------------  ----  ----
0     0              0     SEARCH TABLE words USING COVERING INDEX idx (word>? 
AND word<?) (~55000 rows)
sqlite> explain query plan select * from words where "word" glob 'a' || '%' || 
'a';
sele  order          from  deta
----  -------------  ----  ----
0     0              0     SCAN TABLE words (~500000 rows)



Michael D. Black

Senior Scientist

NG Information Systems

Advanced Analytics Directorate



________________________________
From: sqlite-users-boun...@sqlite.org [sqlite-users-boun...@sqlite.org] on 
behalf of Igor Tandetnik [itandet...@mvps.org]
Sent: Sunday, July 10, 2011 9:22 AM
To: sqlite-users@sqlite.org
Subject: EXT :Re: [sqlite] using index when using concatination

Baruch Burstein <bmburst...@gmail.com> wrote:
> I am using the following SQL statement for SQLite:
>
>    select * from words where "word" like ? || '%' || ? ;
>
> In order to bind parameters to the first and last letters. I have tested
> this both with and without an index on the column `word`, and the results
> are the same. However, when running the queries as
>
>    select * from words where "word" like 'a%a';
>
> etc. (that is, hardcoding each value instead of using ||, the query is about
> x10 faster when indexed.

LIKE comparison may use the index only under certain very limited circumstances 
- see section 4 at

http://sqlite.org/optoverview.html

> Can someone show me how to use both the index and the parameters?

Michael Black's suggestion should work: make it

where word like ?;

build the string of the form "a%b" in your application, and bind it to the 
parameter. Alternatively, you could try something like this:

where word >= :first and word < :next and word like '%' || :last;

Then bind :first as the first letter, :next as the character that immediately 
follows :first in the collation (e.g. if :first is 'a', then :next is 'b'), and 
:last is the last letter.
--
Igor Tandetnik

_______________________________________________
sqlite-users mailing list
sqlite-users@sqlite.org
http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users
_______________________________________________
sqlite-users mailing list
sqlite-users@sqlite.org
http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users
_______________________________________________
sqlite-users mailing list
sqlite-users@sqlite.org
http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users

Reply via email to