2016-07-26 2 views
0

Мы получаем базу данных доступа (.accdb) из внешнего источника и не имеем контроля над структурой или данными. Нам нужно глотать данные в нашу БД с помощью кода. Это означает, что у меня есть контроль над SQL.Предельные записи с SQL в Access

Наша проблема заключается в том, что одна таблица содержит почти 13 тыс. Записей (в настоящее время 12,997) и занимает много времени для обработки. Я хотел бы запросить данные из исходной БД, но только предопределенное количество записей за один раз - скажем, 1000 за раз.

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

SELECT * 
FROM ( 
     SELECT Top + pageSize + sub.* 
     FROM ( 
       SELECT TOP + startPos + [Product Description Codes].* 
       FROM [Product Description Codes] 
       ORDER BY [Product Description Codes].PRODDESCRIPCODE 
     ) sub 
     ORDER BY sub.PRODDESCRIPCODE DESC 
) subOrdered 
ORDER BY subOrdered.PRODDESCRIPCODE 

Где увеличиваем PAGESIZE и StartPos с каждой петлей. Проблема в том, что он всегда возвращает 1000 строк, даже на том, что, как я думаю, должен быть последним циклом, когда он должен возвращать только 997, а затем возвращать ноль после этого.

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

+1

Можете ли вы уточнить, что вы имеете в виду, берет время для обработки? 13k записей ничего и не должно быть медленным –

+0

Прямо сейчас я получаю все 13k записей. Для каждого из них мой код проверяет существующую запись в нашей БД. Если есть существующая запись, она обновляется; если нет существующей записи, вставляется текущая. Я позволил этому запустить вчера, и потребовалось 3,437,640 миллисекунды, что составляет около 57 минут. Это вне наших показателей производительности. – Steve

+1

Я видел ваш комментарий сейчас. Вау, это медленно. Возможно, вы делаете весь процесс неправильным. Похоже, вы делаете операцию один за другим, где только два будут делать? (один для обновления, один для вставки) –

ответ

0

Если PRODDESCRIPCODE является первичным ключом, вы можете упростить выбор. то есть:

SELECT TOP 1000 * ИЗ [коды товара] где PRODDESCRIPCODE> @pcode;

и начать с передачи параметра @pcode 0 (если int или «если текст и т. Д.). В следующем цикле вы должны установить параметр в max PRODDESCRIPCODE, который вы получили.

(Я не уверен, что вы имели в виду MS SQL-сервер, говорящий SQL и как вы это делаете).

+0

PRODDESCRIPCODE - это, действительно, первичный ключ. Когда я говорю «SQL», я имею в виду, что я передаю строку SQL для доступа, используя мой код (который является проприетарной формой или базовым). Я попробую предложение немного и исследую проблему N + 1. – Steve

+0

О, вы передаете строку SQL. Итак, на каком языке? Что такое ваша БД? Можете ли вы сделать это непосредственно из своего БД (программирование на стороне сервера). Я имею в виду, что более подробная информация по этому вопросу будет намного лучше. –

+0

Он называется LIMSBasic, и он является собственностью приложения, которое мы используем под названием LabWare LIMS. Он очень похож (но не идентичен) на Basic. Что еще я могу предоставить? Это мой первый пост здесь, поэтому я хотел бы сделать все, что в моих силах, чтобы помочь вам всем помочь мне. До сих пор я ценю интерес каждого. – Steve

0

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

SELECT PRODDESCRIPCODE, MAX(timestamp) FROM table GROUP BY PRODDESCRIPCODE

Смежные вопросы