Страница 1 из 1

Не используются ключи

Добавлено: 2010-04-16 15:10:09
Alex Keda
вот такое поделие, написанное кода-то давно. и, помоему, раньше ключи использовались.
а может и нет. в любом случае - посещаемость возрасла и я заметил что таблица постоянно пилиться...
начал ковыряться - а тут такое

Код: Выделить всё

mysql> desc counter_segodnya;
+-----------------+-------------+------+-----+------------+----------------+
| Field           | Type        | Null | Key | Default    | Extra          |
+-----------------+-------------+------+-----+------------+----------------+
| id_zapisi       | int(15)     | NO   | PRI | NULL       | auto_increment |
| chislo          | date        | NO   |     | 0000-00-00 |                |
| vremya          | time        | NO   |     | 00:00:00   |                |
| vizit_timestamp | int(16)     | NO   | MUL | 0          |                |
| random_for_jaba | varchar(64) | NO   | MUL | 0          |                |
| ip              | varchar(15) | NO   | MUL |            |                |
| page            | int(5)      | NO   |     | 0          |                |
| user_agent      | text        | NO   |     | NULL       |                |
| referer         | text        | NO   |     | NULL       |                |
| screen_width    | int(6)      | NO   |     | 0          |                |
| screen_height   | int(6)      | NO   |     | 0          |                |
| user_color      | int(6)      | NO   |     | 0          |                |
| word_counter    | int(1)      | NO   | MUL | 0          |                |
+-----------------+-------------+------+-----+------------+----------------+
13 rows in set (0.00 sec)

mysql> explain SELECT COUNT(DISTINCT `ip`) AS `IP_this_day` FROM `counter_segodnya1` WHERE `vizit_timestamp` > '1271361600';
+----+-------------+-------------------+------+-----------------+------+---------+------+--------+-------------+
| id | select_type | table             | type | possible_keys   | key  | key_len | ref  | rows   | Extra       |
+----+-------------+-------------------+------+-----------------+------+---------+------+--------+-------------+
|  1 | SIMPLE      | counter_segodnya1 | ALL  | vizit_timestamp | NULL | NULL    | NULL | 106413 | Using where |
+----+-------------+-------------------+------+-----------------+------+---------+------+--------+-------------+
1 row in set (0.00 sec)
думал из-за условия, но - такое работает нормально.

Код: Выделить всё

mysql> explain SELECT COUNT(DISTINCT `ip`) AS `IP_this_day` FROM `counter_segodnya1` WHERE IP='123';
+----+-------------+-------------------+------+---------------+------+---------+-------+------+--------------------------+
| id | select_type | table             | type | possible_keys | key  | key_len | ref   | rows | Extra                    |
+----+-------------+-------------------+------+---------------+------+---------+-------+------+--------------------------+
|  1 | SIMPLE      | counter_segodnya1 | ref  | ip            | ip   | 17      | const |    1 | Using where; Using index |
+----+-------------+-------------------+------+---------------+------+---------+-------+------+--------------------------+
1 row in set (0.00 sec)

mysql>    

Re: Не используются ключи

Добавлено: 2010-04-16 18:32:56
Fastman
А если явно указать USE INDEX (...)
Просто есть мулька что если использование индекса требует от MySQL прохода более чем по 30% строк в данной таблице то даже при возможности юзания оного, реально индекс юзаться не будет.

Re: Не используются ключи

Добавлено: 2010-04-16 18:46:20
Alex Keda

Код: Выделить всё

mysql> explain SELECT COUNT(DISTINCT `ip`) AS `IP_this_day` FROM `counter_segodnya` WHERE `vizit_timestamp` > '1271361600 USE INDEX ip';
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
| id | select_type | table            | type | possible_keys   | key  | key_len | ref  | rows   | Extra       |
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
|  1 | SIMPLE      | counter_segodnya | ALL  | vizit_timestamp | NULL | NULL    | NULL | 123195 | Using where |
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
1 row in set, 1 warning (0.00 sec)

mysql> explain SELECT COUNT(DISTINCT `ip`) AS `IP_this_day` FROM `counter_segodnya` WHERE `vizit_timestamp` > '1271361600 USE INDEX vizit_timestamp';
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
| id | select_type | table            | type | possible_keys   | key  | key_len | ref  | rows   | Extra       |
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
|  1 | SIMPLE      | counter_segodnya | ALL  | vizit_timestamp | NULL | NULL    | NULL | 123197 | Using where |
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
1 row in set, 1 warning (0.00 sec)

mysql>    

Re: Не используются ключи

Добавлено: 2010-04-16 20:03:49
dikens3
)) Юзайте postgresql... )) В mysql оптимизатор гавно. Думаю из-за знака ">"
Балуйся ключами, я так делал.

Re: Не используются ключи

Добавлено: 2010-04-16 20:16:48
Fastman
dikens3 писал(а):)) Юзайте postgresql... )) В mysql оптимизатор гавно. Думаю из-за знака ">"
Балуйся ключами, я так делал.
Причина всегда есть. Если мы ее не знаем это не значит что MySQL Говно...
Вообщем я пас если честно... опыта в MySQL не много....

Re: Не используются ключи

Добавлено: 2010-04-16 23:00:53
dikens3
Если мы ее не знаем это не значит что MySQL Говно...
Не mysql, а оптимизатор - который решает как и какие ключи использовать.

Re: Не используются ключи

Добавлено: 2010-04-17 8:46:41
Alex Keda
так тоже некатит

Код: Выделить всё

mysql> explain SELECT COUNT(DISTINCT `ip`) AS `IP_this_day` FROM `counter_segodnya` WHERE `vizit_timestamp` between '1271361600' and 10000000000;
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
| id | select_type | table            | type | possible_keys   | key  | key_len | ref  | rows   | Extra       |
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
|  1 | SIMPLE      | counter_segodnya | ALL  | vizit_timestamp | NULL | NULL    | NULL | 130678 | Using where |
+----+-------------+------------------+------+-----------------+------+---------+------+--------+-------------+
1 row in set (0.01 sec)

mysql>   

Re: Не используются ключи

Добавлено: 2010-04-17 11:26:37
dikens3
Я знаешь как решил свою проблему? Создал ещё один столбец(всегда одинаковый) и создал двойной ключ.

Т.е. у тебя есть:
Столбец X (нужный тебе и не работающий с индексом)
+ Новый столбец (скажем писать туда 1)

Ключ одновременно на оба.

Потом делал если СТАРОЕ_УСЛОВИЕ и НОВЫЙСТОЛБЕЦ=1

Что-то типа того:

Код: Выделить всё

# Создаём таблицу логов.
DROP TABLE IF EXISTS `log`;
CREATE TABLE `log` (
  `username` varchar(50) default NULL,
  `action` smallint(6) unsigned NOT NULL default '0',
  `src_email` varchar(50) default NULL,
  `dst_email` varchar(50) default NULL,
  `src_ip` varchar(15) default NULL,
  `hostname` varchar(255) default NULL,
  `helo` varchar(255) default NULL,
  `date` date default NULL,
  `size` int(11) default NULL,
  `time` timestamp NOT NULL default '',
  KEY `size-date` (`size`,`date`),
  KEY `action-date` (`action`,`date`),
  KEY `size` (`size`),
  KEY `date` (`date`)
) ENGINE=MyISAM DEFAULT CHARSET=koi8r COMMENT='Таблица логов';