Будет ли быстрее использовать несколько потоков для обновления одной и той же базы данных? - PullRequest
2 голосов
/ 23 сентября 2008

Я написал программу на Java для добавления и извлечения данных из MS Access. В настоящее время он проходит последовательно через ~ 200 тыс. Запросов на вставку за ~ 3 минуты, что я считаю медленным. Я планирую переписать его, используя потоки с 3-4 потоками, обрабатывающими разные части сотен тысяч записей. У меня сложный вопрос:

  • Поможет ли это ускорить выполнение программы из-за разделенной рабочей нагрузки или будет таким же, потому что потоки все равно должны последовательно обращаться к базе данных?

  • Какая стратегия, по вашему мнению, ускорит этот процесс (за исключением оптимизации запросов, которую я уже сделал в дополнение к использованию подготовленного состояния Java)

Ответы [ 8 ]

3 голосов
/ 23 сентября 2008
  1. Не знаю. Не зная больше о том, что такое горлышко бутылки, я не могу комментировать, будет ли это быстрее. Если база данных является ограничителем, скорее всего, большее количество потоков замедлит ее.

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

2 голосов
/ 23 сентября 2008

Во-первых, не используйте Access. Переместите свои данные куда угодно - SQL / Server - MySQL - что угодно. Механизм DB внутри доступа (называемый Jet) жалко медленен. Это не настоящая база данных; это для личных проектов, которые включают небольшие объемы данных. Это не масштабируется вообще.

Во-вторых, потоки редко помогают.

Соединение JDBC с базой данных является ресурсом всего процесса. Все темы разделяют одно соединение.

«Но подождите, - говорите вы, - я создам уникальный объект Connection в каждом потоке».

Благородно, но иногда обречено на провал. Зачем? Обработка операционной системы между вашей JVM и базой данных может включать в себя сокет, который представляет собой единый ресурс для всего процесса, который используется всеми вашими потоками.

Если у вас есть один ресурс ввода-вывода на уровне ОС, который совместно используется всеми потоками, вы не увидите значительных улучшений. В этом случае соединение ODBC является одним узким местом. И MS-Access другой.

1 голос
/ 25 сентября 2008

Я бы согласился, что дамп Access будет лучшим первым шагом. Сказав это ...

В среде .NET и SQL я определенно видел, как потоки помогают максимизировать пропускную способность INSERT.

У меня есть приложение, которое принимает асинхронные удаления файлов, а затем обрабатывает их в виде таблиц в базе данных.

Я создал загрузчик, который проанализировал файл и поместил данные в очередь. Очередь обслуживалась одним или несколькими потоками, максимум которых я мог настроить с помощью параметра. Я обнаружил, что даже на одноядерном процессоре с обычным диском 7200 об / мин идеальное количество рабочих потоков составляло 3. Это сокращало время загрузки почти пропорционально. Ключ заключается в том, чтобы сбалансировать его так, чтобы узкое место ЦП и узкое место дискового ввода-вывода были сбалансированы.

Так что в случаях, когда массовая копия не является опцией, следует рассмотреть потоки.

1 голос
/ 23 сентября 2008

Подход с массовой загрузкой Stimms, вероятно, будет лучшим выбором, но все стоит попробовать один раз. Обратите внимание, что ваша горловина бутылки будет дисковым вводом-выводом, и несколько потоков могут замедлить процесс. Доступ MS также может развалиться, когда несколько пользователей стучат по файлу, и именно так будет действовать ваш многопоточный подход (сделайте резервную копию!) Если производительность по-прежнему остается проблемой, рассмотрите возможность обновления до SQL express .

MS Access к документам по миграции на SQL Server.

Удачи.

1 голос
/ 23 сентября 2008

С MSAccess в качестве внутренней базы данных вы, вероятно, получите лучшую производительность вставки, если выполните импорт из MSAccess. Другой вариант (поскольку вы используете Java) - это напрямую манипулировать файлом MDB (если вы создаете его с нуля, и нет других одновременно работающих пользователей - с которым MS Access не очень хорошо справляется) с помощью библиотеки, подобной Jackess .

Если ни одно из этих решений не является для вас решением, я бы порекомендовал использовать профилировщик в своем приложении Java и посмотреть, тратит ли оно большую часть времени на ожидание базы данных (в этом случае добавление потоков, вероятно, не очень поможет). ) или если это делает обработку и распараллеливание поможет.

0 голосов
/ 25 сентября 2008

Доступ IIRC не позволяет нескольким подключениям к одному файлу из-за политики блокировки, которую он использует.

И я полностью согласен с демпингом доступа для sql.

0 голосов
/ 23 сентября 2008

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

0 голосов
/ 23 сентября 2008

На современных многоядерных машинах использование нескольких потоков для заполнения базы данных может иметь значение. Это зависит от базы данных и ее оборудования. Попробуйте и посмотрите.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...