Форум успешных вебмастеров - GoFuckBiz.com

  Форум успешных вебмастеров - GoFuckBiz.com > Бизнес-решения > Скрипты, программы и технические решения
Дата
USD/RUB58.7570
BTC/USD0.0000
Скрипты, программы и технические решения Обсуждаем скрипты, программы и новые технологии.

Закрытая тема
Опции темы Опции просмотра
Старый 31.01.2011, 20:41   #1
chesser
автоматизирую интернеты
 
Аватар для chesser
 
Регистрация: 05.07.2009
Адрес: chesser.ru
Сообщений: 3,382
Бабло: $470735
По умолчанию хайлоад оптимизация

Может поможет кто... Есть один производственный процесс, который жутко тормозил ввиду моей криворукости и малоопытности в хайлоаде.
Сейчас я наоптимизировал - стало получше, но подозреваю, что можно еще повысить скорость.

Процесс наполняет две таблицы в БД значениями и далее делаются выборки. Что есть на данный момент:
PHP код:
CREATE TABLE `tbl1` (
 `
hashint(11unsigned NOT NULL,
 `
valuevarchar(255NOT NULL,
.......
 
PRIMARY KEY (`value`)
ENGINE=MyISAM


CREATE TABLE 
`tbl2` (
 `
hash1int(11unsigned NOT NULL,
 `
hash2int(11unsigned NOT NULL,
.......
 
PRIMARY KEY (`hash1`,`hash2`)
ENGINE=MyISAM 
При обработки эти таблицы на самом деле ENGINE=MEMORY, но периодически сейвятся и мержаться с MyISAM

типичные упрощенные запросы на вставку:
PHP код:
  INSERT INTO tbl1 (hashvalue)    VALUES(CRC32('$value'), '$value'ON DUPLICATE UPDATE ......;
  
INSERT INTO tbl2 (hash1hash2VALUES($hash1$hash2ON DUPLICATE UPDATE ......; 
типичный запрос на выборку:
PHP код:
  SELECT hash2 FROM tbl2 WHERE hash1=$value 
хеши, как видно выше, 4-х байтовые числовые, сделано специально, чтобы индексы шустрее работали(по числам)
Процент коллизий надеюсь будет маленький да и это не подводная лодка, поэтому crc32 мне отлично подошел, но все-таки пока временно оставил primary key по значению.

Теперь проблемы какие.

1. Как оптимальнее всего взять рандомную строку из tbl2 ?

ожидаемое кол-во записей более 100кк, поэтому order by rand и limit тут плохо работают, а новое поле с автоинкрементом вводить накладно, распределение хешей hash1 не равномерное, средняя прореженность хешей(или как это называется) соответственно 4байта/100кк = 42, но из-за неравномерности гадать можно будет долго, если пытаться угадать

2. Может есть какое-то более продвинутое решение моей задачи.
мельком смотрел memcached и redis - все красиво, первую таблицу можно туда перевести. Но как мне на них организовать мою выборку по второй таблице? т.е. мне нужно брать одно свойство объекта(hash2), на основании другого(hash1)

3. где бы хешировать(crc32) данные, чтобы свой сервер не грузить? мож есть фри аутсорс какой-то? CUDA наверно нужна, а где ее взять в инете фор фри?

вообще есть идея сделать воркер-скрипты на php и загружать их на фрихосты, далее слать задания на хеширование. Либо тоже самое, только скрипты на js и давать их в браузер дешовому трафу, чтобы браузер хешировал...пусть хоть хеши считают, раз денег не приносят

ps: знаю, что форумом ошибся, но я люблю этот, может кто подкинет идей
__________________
USA и NL серверы и VPS | wiki | блог | Drupal | NginxТДС
Ave, Google, morituri te salutant! © chesser
chesser вне форума  
Старый 31.01.2011, 20:53   #2
kaufman
да, я за мир
 
Аватар для kaufman
 
Регистрация: 30.11.2010
Сообщений: 948
Бабло: $156900
По умолчанию

По выборке случайных записей посмотри эти статьи, может пригодится:
http://habrahabr.ru/blogs/mysql/54176/
http://habrahabr.ru/blogs/mysql/55864/

По вычислению хешей - идея вынести в js интересная. Попробуй на китайском трафе. Надо оценить накладные расходы: траффик+ресурсы на выдачу задания/приемку хешей от клиентов.
__________________
Криптор/обфускатор для JS скриптов
* привязка к домену * установка времени жизни скрипта * открытый код обфускатора
kaufman вне форума  
Старый 31.01.2011, 21:04   #3
ar4ibas
Senior Member
 
Регистрация: 11.11.2009
Сообщений: 362
Бабло: $71310
По умолчанию

уточни где именно тормоза, в первой фазе "Процесс наполняет две таблицы в БД значениями" или в фазе "типичный запрос на выборку"

какая версия мускула? сколько записей в таблице?

есть кое каие идеи

исходя из того что я понял на данный момент

-при вставке, если она в цикле очень выручат препаред стайтментс, вставка блоками, отключение ключей на период вставки
-под твои таблицы пездато подойдет партиционирование
-про рандомную строку тема избита, гугли
-по мемкешу все четко должно сраюботать, hash1 у тебя ключ а hash2 значение
-лихо придумал с обработкой срс на клиентах, но думаю идея обречена на провал

а вобще схема стандартная
-пробуй партиционировать
-потом если не помогло - пробуй репликацию
-потом если не помогло - пробуй шардить

Последний раз редактировалось ar4ibas; 31.01.2011 в 21:14.
ar4ibas вне форума  
Старый 01.02.2011, 05:00   #4
chesser
автоматизирую интернеты
 
Аватар для chesser
 
Регистрация: 05.07.2009
Адрес: chesser.ru
Сообщений: 3,382
Бабло: $470735
ТС -->
автор темы ТС По умолчанию

версия mysql 5.1 - но вообще, могу сделать какую надо.
Сейчас во второй таблице 0 записей, через час работы софта в ней становиться около 15млн записей, через еще час прибавляется еще 5 млн и тд, во время тестов доводил до 80млн. В реале будет от 100 до 1000 млн - думаю можно назвать ее таблицей синапсов, а первую таблицу - нейронами, поэтому столько много, причем в этих 100млн каждая запись после создания апдейтится в среднем более 1к раз - это идет как бы калибровка синапсов.
Конкретно сейчас я пытаюсь ускорить вставку и апдейт этих таблиц, т.е. процесс обучения НС. Дальше придется думать как убыстрять пользование НС - т.е. селекты. Основное отличие - максимально убрать индексы во время обучения таблиц, и наоборот - проставить необходимые индексы при использовании.

про рандом.
все эти способы я видел и пробовал, самый быстрый это "where id=100500" - раньше так и работало, когда был primary key типа unsigned int auto_increment, при более-менее равномерной разряженности id выборка равномерная, но со временем при появлении дыр в индексе равномерность пропадает. Да и поле новое не хочется добавлять, за ним следить надо и места займет еще прилично, а памяти и так мало. Буду думать велосипед, как из crc32 хешей выбирать рандом.

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

Цитата:
-по мемкешу все четко должно сраюботать, hash1 у тебя ключ а hash2 значение
а оно быстрее будет MySQL MEMORY ? ну или HEAP таблицами их раньше называли, в раме располагаются, вроде быстро работают и могут строить хеш-индексы - ими я и пользуюсь, правда периодически приходиться сохранять результат в MyISAM
Как hash1 ключем, если эта колонка неуникальна сама по себе, а уникальны только сочетания hash1,hash2. По идеи кеем будет hash1_hash2 => value - но тогда как делать выборки по частям этого ключа.
Еще такой момент, я забыл прорисовать в структуре, помимо hash1=>hash2 нужны обратные связи: hash2=>hash1
Цитата:
SELECT hash1 FROM tbl2 WHERE hash2=$value1
SELECT hash2 FROM tbl2 WHERE hash1=$value2
__________________
USA и NL серверы и VPS | wiki | блог | Drupal | NginxТДС
Ave, Google, morituri te salutant! © chesser
chesser вне форума  
Старый 01.02.2011, 05:08   #5
chesser
автоматизирую интернеты
 
Аватар для chesser
 
Регистрация: 05.07.2009
Адрес: chesser.ru
Сообщений: 3,382
Бабло: $470735
ТС -->
автор темы ТС По умолчанию

Цитата:
Сообщение от ar4ibas Посмотреть сообщение
-лихо придумал с обработкой срс на клиентах, но думаю идея обречена на провал
да и на фрихостах тоже можно замутить, вот только crc32 не настолько серьезный хеш, чтобы его делегировать, издержки на транспорт данных могут выйти больше. Может sha1 считать и есть смысл.
Я думал, может кто-то уже так делает? собирают же люди md5 хеши килотоннами для вредных целей

Цитата:
Сообщение от ar4ibas Посмотреть сообщение
а вобще схема стандартная
-пробуй партиционировать
-потом если не помогло - пробуй репликацию
-потом если не помогло - пробуй шардить
про партицирование в mysql не знал - спс, хотя в моем случае оно не катит, т.к. я не могу логически поделить данные на части по частоте использования, например. А просто разбить таблицу на разные части - она у меня и так разбивается на MEMORY таблицы....ну короче это следующий этап и остальные пункты тоже когда логика уже не будет помогать
__________________
USA и NL серверы и VPS | wiki | блог | Drupal | NginxТДС
Ave, Google, morituri te salutant! © chesser
chesser вне форума  
Старый 01.02.2011, 06:11   #6
chesser
автоматизирую интернеты
 
Аватар для chesser
 
Регистрация: 05.07.2009
Адрес: chesser.ru
Сообщений: 3,382
Бабло: $470735
ТС -->
автор темы ТС По умолчанию

Цитата:
Сообщение от я разговариваю сам с собой
Не совсем пока понимаю, как это организовать с препаредами
не знал что препаред стейтменты можно объединять с ON DUPLICATE KEY
Цитата:
INSERT INTO tbl1(hash1,hash2) VALUES ( 1, 2 ) , (3, 4 ) , ( 1,2) , (3, 4,) ON DUPLICATE KEY UPDATE freq = freq +1
надеюсь это даст ощутимый прирост, завтра буду пробовать
__________________
USA и NL серверы и VPS | wiki | блог | Drupal | NginxТДС
Ave, Google, morituri te salutant! © chesser
chesser вне форума  
Старый 01.02.2011, 14:00   #7
ar4ibas
Senior Member
 
Регистрация: 11.11.2009
Сообщений: 362
Бабло: $71310
По умолчанию

-вот линка полезная про партиции в мускуле http://habrahabr.ru/blogs/webdev/66151/

-MEMORY vs memcache http://stackoverflow.com/questions/9...able-like-heap
это я бы сказал специфично для каждой задачи, кому мемкеш кому мускул мемори

если вставки происходят одновременно с селектами то лучше включай innodb вместо myisam. если же сначала идут только вставки а потом только селекты то оставь как есть myisam

чисто теоретически думаю стоит проверить возможность сменить тип поля у hash с int(11) unsigned NOT NULL на char(8) если у тебя crc32 хеши. это даст экономию 3 байта на запись (итого экономия 3 х 100 млн байт)

я бы на твоем месте попробовал mongodb вместо мускуля так как у тебя простые запросы и простая структура, атомарности не требует а в мускуле как известно SQL уровень очень дорогой. монго является persistent хранилищем в отличие от мемкеша, говорят шустрая штуковина, масштабируется очень просто, вот здесь почитай

http://highload.com.ua/index.php/201...-db-and-mysql/
http://highload.com.ua/index.php/201...а-mongodb-php/

Последний раз редактировалось ar4ibas; 01.02.2011 в 14:15.
ar4ibas вне форума  
Старый 01.02.2011, 14:28   #8
ar4ibas
Senior Member
 
Регистрация: 11.11.2009
Сообщений: 362
Бабло: $71310
По умолчанию

Цитата:
Сообщение от ar4ibas Посмотреть сообщение
если вставки происходят одновременно с селектами то лучше включай innodb вместо myisam. если же сначала идут только вставки а потом только селекты то оставь как есть myisam
бля я чето протупил, ты же мемори юзаешь

Цитата:
Сообщение от ar4ibas Посмотреть сообщение
чисто теоретически думаю стоит проверить возможность сменить тип поля у hash с int(11) unsigned NOT NULL на char(8) если у тебя crc32 хеши. это даст экономию 3 байта на запись (итого экономия 3 х 100 млн байт)
чето я ерунду написал


а вот про монгодб походу правду сказал

Последний раз редактировалось ar4ibas; 01.02.2011 в 14:38.
ar4ibas вне форума  
Старый 01.02.2011, 15:51   #9
buddy
Member
 
Регистрация: 14.04.2007
Сообщений: 70
Бабло: $9415
По умолчанию

Цитата:
Сообщение от chesser Посмотреть сообщение
1. Как оптимальнее всего взять рандомную строку из tbl2 ?
может так
если tbl2.hash1 это crc32 и есть индекс по tbl2.hash1 тогда
select hash2 from tbl2 where tbl2.hash1>crc32(rand()) order by tbl2.hash1 desc limit 1;
__________________
DNS Report
buddy вне форума  
Старый 01.02.2011, 17:03   #10
xanxy
Senior Member
 
Регистрация: 18.08.2010
Сообщений: 361
Бабло: $66100
По умолчанию

Вообще MyISAM есть такая охуенная штука как insert delayed, но не под все задачи подходит. Там в запросе на вставку не написано что делается в ON DUPLICATE UPDATE, может можно использовать REPLACE?
Во второй таблице праймари кей из двух слобцов, я так понимаю мускуль для них замутит cовмесный индекс, а значит SELECT hash2 FROM tbl2 WHERE hash1=$value будет работать медленнее, чем если бы было два раздельных индекса, думаю стоит тупо добавить два индекса на hash1 hash2.
И старайся вставки делать не по одному, а накапливать вставлять по 50 записей к примеру.

под нейронки есть либа http://leenissen.dk/fann/

Да и по моему юзать MEMORY а потом мержить не очень производительно будет. Там ведь блокировки и тд..

Последний раз редактировалось xanxy; 01.02.2011 в 17:15.
xanxy вне форума  
Закрытая тема



Опции темы
Опции просмотра