на 1 млрд 54 млн строк. Сперва я хотел загнать его с условиями
str varchar UNIQUE NOT NULL
но потом сдался, сейчас добавляю вообще
str varchar
то есть уже убрал проверку на уникальность, убрал всё. Файл имеет особенность, там проблемы с кодировкой, не всё utf8 корректно, поэтому copy into не сработает.
Проблема.
Все эксперименты не уводят меня с одной скорости добавления до 1.5 млн строк в сутки. При этом работаю на локалхосте добавляю с java обычный update, файл с данными и база на разных винтах. ПЖ 13.
Вопрос.
нормальные ли это цифры? Может это какие то внутренние ограничения?
Во первых если у вас жесткий диск то они медленные. Предположил потому что вы говорите винт. Во вторых раз не все у вас валидный utf-8, то возможно стоит добавлять через COPY в бинарном виде, а обрабатывать уже потом?
У вас структура таблички какая?
как вы из джава используя update заливаете данные?
не понимаю вопрос. Беру update. И заливаю. Может вопрос делаю ли ? вместо переменной прямо в запрос? Да, делаю, чтобы ошибок не было.
я тоже не понял. заливают обычно insert/copy команду покажите
query = "INSERT INTO strtabltest(str) VALUES(?)"; pst.setString(1, readstr); pst.executeUpdate();
а массивом залить не можете? не по одному значению, а сразу массив
как это? Я вот тут задумался, добавить по 50 строк. VALUES(?),(?),(?)...,(?) Сейчас попробую. А целый массив как? У меня оперативной памяти всего 8 гб. зы, попробую в смысле пишу в джава.
можете и так попробовать, но в идеале вам выше написали COPY
Нашел в одном блоге упоминание http://ossc-db.github.io/pg_bulkload/index.html Не использовал, не знаю что из себя представляет.
Нет, ненормальны, это очень мало.
И да, при добавлении записей не должно быть ни одного update...
а сколько нормально? На сколько обычно база данных постгрес утилизирует скорость дисковой подсистемы? Допустим 1 гб строковый файл на 1 hdd (150 мегабайт в секунду), добавляем его в таблицу с одним полем 2 hdd (150 мегабайт). Копирование займёт ожидаемое время. А insert в базу?
Если не очень забит и совсем без индэксов -- то где-то раза в три-пять медленнее. С одним индэксом на id -- ещё надо думать раз в полтора-два.
hdd, 20 в секунду? autocommit небось стоит. Числа похожые.
не понятно. то есть без индексов 30-50 мегабайт в секунду, а с индексом id — 100 мегабайт?
если вы делаете это в один поток то вас ни что не спасет чтобы нагрузить диск таким образом, даже один, надо делать вставку параллельно в несколько потоков
не совсем понимаю логику. один поток получает данные и тут же отправляет их в таблицу. несколько потоков. Также один поток получает данные, чтение с винта то отлично идёт, я файл вообще на ssd положил. А вот как поможет несколько потоков pg для insert в одну таблицу? Почему несколько подлючений для пж будет лучше?
Там было слово "ещё".
Не особенно надо. Чуть-чуть можэт подняться, на SSD можэт и во сколько-то раз подняться (в мало раз). Но в общем -- много от этого не выиграть.
опять же почему? Программа простейшая, у меня не куча, с постоянным заполнением в java 2 потока, один читает и заполняет, а второй записывает даннные в пж. А один поток, массив. Конечно, мне логично читать как можно быстрее файл.
Не забивайте себе мозг. Сначала проверьте autocommit. Потом, если не поможэт -- скорость формирования вашых строк (например, заменив insert на константу).
я выше писал. Я сделал запись не по одному значению, а по 50 за раз. Скорость увеличилась в несколько раз.
Такая задача решается через batch insert в jdbc, точного синтаксиса не вспомню. Размер батча подбирается по производительности, но там будет порядка 1000 вставок, а не 50.
спасибо, почитаю. зы мне кстати это уже писали, я забыл проверить. Эх я...
В несколько -- это тожэ очень мало. Если бы дело было только в автокоммите, то вставка по 50 строк ускорила бы в 50 раз. Кроме того, в общем ускорение менее чем в 1000 раз -- это мало само по себе.
ясно. Я живу в физическом мире, а не матрице. На винт в 180 мегабайт оптимистичной скорости никак в 1000 раз не увеличу вставку данных.
На винт в 180 мегабайт оптимистичной скорости никак в 1000 раз не увеличу вставку данных. ну можно поставить zfs а там ОЗУ побольше и можно ускорить если не в 100 раз то довольно существенно
да чо тянуть, сразу оперативки терабайт и рам диск, в него базу.
У вас в среднем по 30 байт на строку. Делим 180 мегабайт в секунду на 30 байт на строку -- получаем 6 миллионов записей в секунду. Делим ещё, допустим, на 10 (затраты на ACID) -- получаем 600 тысяч записей в секунду. Это в общем тот лимит, вышэ которого нет большого смысла пытаться перепрыгнуть -- но к которому можно стремиться. У вас, вы говорите, было 1.5 миллиона записей в сутки. Делим на количество секунд в сутках -- получается 20 записей в секунду. В 1000 раз большэ, чем 20 записей в секунду -- это 20 000 записей в секунду. Или в 30 раз медленнее, чем оцэнка того, к чему можно при жэлании стремиться и в 300 раз медленнее, чем скорость вашэго жёсткого диска. Это не быстро. Скорость в 1000 раз большэ, чем у вас в оригинале -- это небыстро. Но ужэ нормально. И это даст загрузку вашэго датасета за сутки. Что, в общем, тожэ не так плохо. Скорость в 100 записей в секунду, нет, пусть дажэ дажэ в 1000 записей в секунду -- это с одной стороны в сотни раз медленнее чем расчётный лимит, а с другой стороны -- это загрузка вашэго датасета за три недели. Это ненормально ни с какой стороны.
Обсуждают сегодня