简体   繁体   中英

How to improve search performance in MySQL

I have a table that contains two bigint columns: beginNumber , endNumber , defined as UNIQUE . The ID is the Primary Key .

ID | beginNumber | endNumber | Name | Criteria

The second table contains a number. I want to retrieve the record from table1 when the Number from table2 is found to be between any two numbers. The is the query:

select distinct t1.Name, t1.Country
from t1
where t2.Number
BETWEEN t1.beginIpNum AND t1.endNumber

The query is taking too much time as I have so many records. I don't have experience in DB. But, I read that indexing the table will improve the search so MySQL does not have to pass through every row searching about m Number and this can be done by, for example, having UNIQE values. I made the beginNumber & endNumber in table1 as UNIQUE. Is this all what I can do ? Is there any possible way to improve the time ? Please, provide detailed answers.

EDIT:

table1:

CREATE TABLE `t1` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `beginNumber` bigint(20) DEFAULT NULL,
  `endNumber` bigint(20) DEFAULT NULL,
  `Name` varchar(255) DEFAULT NULL,
  `Criteria` varchar(455) DEFAULT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `beginNumber_UNIQUE` (`beginNumber`),
  UNIQUE KEY `endNumber_UNIQUE` (`endNumber `)
) ENGINE=InnoDB AUTO_INCREMENT=327 DEFAULT CHARSET=utf8

table2:

CREATE TABLE `t2` (
  `id2` int(11) NOT NULL AUTO_INCREMENT,
  `description` varchar(255) DEFAULT NULL,
  `Number` bigint(20) DEFAULT NULL,
  PRIMARY KEY (`id2`),
  UNIQUE KEY ` description _UNIQUE` (`description `)
) ENGINE=InnoDB AUTO_INCREMENT=433 DEFAULT CHARSET=utf8

This is a toy example of the tables but it shows the concerned part.

I'd suggest an index on t2.Number like this:

ALTER TABLE t2 ADD INDEX numindex(Number);

Your query won't work as written because it won't know which t2 to use. Try this:

SELECT DISTINCT t1.Name, t1.Criteria
FROM t1 
WHERE EXISTS (SELECT * FROM t2 WHERE t2.Number BETWEEN t1.beginNumber AND t1.endNumber);

Without the t2.Number index EXPLAIN gives this query plan:

1   PRIMARY t1  ALL                 1   Using where; Using temporary
2   DEPENDENT SUBQUERY  t2  ALL                 1   Using where

With an index on t2.Number, you get this plan:

PRIMARY t1  ALL                 1   Using where; Using temporary
DEPENDENT SUBQUERY  t2  index   numindex    numindex    9       1   Using where; Using index

The important part to understand is that an ALL comparison is slower than an index comparison.

This is a good place to use binary tree index (default is hashmap). Btree indexes are best when you often sort or use between on column.

CREATE INDEX index_name

ON table_name (column_name)

USING BTREE

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM