SQLinfo.ru - Все о MySQL

Форум пользователей MySQL

Задавайте вопросы, мы ответим

Вы не зашли.

#1 01.09.2009 22:43:41

Mouse
Участник
Зарегистрирован: 01.09.2009
Сообщений: 7

Оптимизация запроса

Здравствуйте! Помогите оптимизировать запрос. По моему не очень "красиво" получается. Два подзапроса к одной и тойже таблице в одном запросе по моему многовато. Буду благодарен за любую помощь!

Есть 2 таблицы с рекламой (Users_ad, Users_ad_arch), первая рабочая, вторая архивная. Обе таблицы абсолютно идентичны. Таблица  рекламных каманий (Users_ad_camp) и таблица статистики (Log_ad).

Нужно на выходе получить:
- название рекламной кампании
- количество активной рекламы
- количество выключенной рекламы
- всего показов по рекламной кампании за сегодня
- всего кликов за сегодня
- всего CTR за сегодня

Версия сервера MySQL: 4.1.22

Таблицы:

CREATE TABLE Log_ad (
  ad_id int(11) NOT NULL default '0',
  view int(11) NOT NULL default '0',
  click int(11) NOT NULL default '0',
  `date` date NOT NULL default '0000-00-00',
  PRIMARY KEY  (ad_id,`date`),
  KEY `date` (`date`),
  KEY ad_id (ad_id)
) ENGINE=MyISAM;

CREATE TABLE Users_ad (
  id int(11) NOT NULL auto_increment,
  camp_id int(11) NOT NULL default '0',
  title varchar(50) NOT NULL default '',
  body varchar(150) NOT NULL default '',
  url varchar(250) NOT NULL default '',
  PRIMARY KEY  (id),
  KEY camp_id (camp_id)
) ENGINE=MyISAM;

CREATE TABLE Users_ad_arch (
  id int(11) NOT NULL auto_increment,
  camp_id int(11) NOT NULL default '0',
  title varchar(50) NOT NULL default '',
  body varchar(150) NOT NULL default '',
  url varchar(250) NOT NULL default '',
  PRIMARY KEY  (id),
  KEY camp_id (camp_id)
) ENGINE=MyISAM;

CREATE TABLE Users_ad_camp (
  id int(11) NOT NULL auto_increment,
  title varchar(250) NOT NULL default '',
  PRIMARY KEY  (id),
  KEY user_id (user_id)
) ENGINE=MyISAM;


Вот что у меня получилось:

SELECT c.title,(SELECT COUNT(*) from Users_ad a WHERE camp_id=c.id) as bcnt,(SELECT COUNT(*) from Users_ad_arch WHERE camp_id=c.id) as bcnta,SUM(ls.view) as sview,SUM(ls.click) as sclick,(SUM(ls.click)/SUM(ls.view)*100) as ctr from Users_ad_camp c LEFT JOIN Log_ad ls ON (ls.ad_id IN (SELECT id from Users_ad WHERE camp_id=c.id UNION SELECT id from Users_ad_arch WHERE camp_id=c.id) AND ls.date=CURDATE()) GROUP BY c.id


Мне кажется, что при большом количестве записей в таблице такой запрос будет тормозить.

Отредактированно Mouse (01.09.2009 22:47:01)

Неактивен

 

#2 02.09.2009 01:30:34

vasya
Архат
MySQL Authorized Developer
Откуда: Орел
Зарегистрирован: 07.03.2007
Сообщений: 5842

Re: Оптимизация запроса

Например, вы можете хранить избыточную информацию.
Количество активной/выключенной рекламы для данной компании изменяется, наверное, не очень часто, поэтому имеет смысл хранить эту информацию.

Неактивен

 

#3 02.09.2009 11:14:42

Mouse
Участник
Зарегистрирован: 01.09.2009
Сообщений: 7

Re: Оптимизация запроса

Информация может меняться довольно часто. Думаю такой способ не совсем подойдет.

Неактивен

 

#4 02.09.2009 13:35:32

vasya
Архат
MySQL Authorized Developer
Откуда: Орел
Зарегистрирован: 07.03.2007
Сообщений: 5842

Re: Оптимизация запроса

Немного беспредметный разговор получается - "часто", "довольно часто"..

Хранить избыточную информацию имеет смысл если количество запросов на чтение значительно превышает количество запросов на запись. Насколько я могу судить из логики запроса, это и есть ваш случай.

Неактивен

 

#5 02.09.2009 14:16:36

Mouse
Участник
Зарегистрирован: 01.09.2009
Сообщений: 7

Re: Оптимизация запроса

Как раз наоборот. Количество запросов на запись значительно больше, чем запросов на чтение.

В таблицу статистики (Log_ad) записываются данные по показам и кликам. Количество рекламы в рекламной кампании может изменяться. А сам запрос показывает статистические данные только по запросу пользователя.

P.S. Насколько грамотно сконструированы таблицы и запрос к ним?

Отредактированно Mouse (02.09.2009 14:20:04)

Неактивен

 

Board footer

Работает на PunBB
© Copyright 2002–2008 Rickard Andersson