Хранение матриц в базе данных
Я работаю над проектом для клиента и прохождения начального этапа проектирования базы данных. Проект будет простым веб-приложением для отслеживания процессов и их результатов в матричной диаграмме, я ищу хороший способ сохранить их в реляционных таблицах.
прямо сейчас я думаю, что у меня есть общая таблица для подпрограмм, которые координаты x и y тоже будут отображаться и, возможно, от этой таблицы поиска, содержащей идентификатор координат, в которых записывается «хит». Кто-нибудь есть лучшие способы сделать это?
Это только начало проекта, поэтому у меня пока ограниченная детализация, но мои основные рассуждения о нескольких таблицах заключаются в том, что матрицы будут полностью динамическими по размеру и общими, так что каждый из них может быть разным, и они будут привязаны к пользователю
Я также забыл упомянуть, что порядок значений x/y важен, что дополнительно подтвердило мои рассуждения о том, что несколько таблиц для x y и значений, из этого я сильно предполагаю, что важно знать каждую отдельную ячейку
основной пример (хотя и абстрактный) этого лежит в процессе, касающемся ресторана. Действия-это вещи вдоль линий сесть, заказать еду, просмотреть меню, заказать напитки, поесть, заплатить и т. д. результаты принимаются заказ, напитки доставлены, еда доставлена, изменения даны. В то время как кажущийся простым он становится сложным, когда принимается рассмотрение вещи происходят по-разному с каждым возникновением, также в случае вынимают или буфеты. порядок действий и результатов становится неотъемлемым в видении различий между ситуациями
4 ответов
есть много способов сделать это, нам понадобится гораздо больше информации, чтобы быть более конкретными о том, что было бы лучше для вас. Однако вот два способа SOP:
либо отдельная таблица для каждой матрицы:
или, все матрицы в одну таблицу:
это стандартная нормальная форма, практически все другие способы не нормализуется. Некоторые преимущества этих подходов:
- вы не нужно заполнять каждую ячейку, только те, которые вы используете. Или иметь значение по умолчанию (0 или «») и пропустить те.
- это легко самый гибкий подход, даже в модели «все в одном», нет необходимости каким-либо образом ограничивать их одинаковым размером, и их очень легко изменить размер.
- вы можете легко запросить содержание матрицы, что-то, что становится все труднее в более компактном хранилище методы.
- » Hit » s или любой другой аспект ячеек матрицы легко реализовать в качестве дополнительных полей в строках. Сделайте их Null-able, если вы беспокоитесь о дополнительном пространстве, и индексируйте их, если вы хотите запросить/сообщить об этих атрибутах отдельно. Свой также как раз как легкий для того чтобы retrofit характеристики как это с этой моделью также.
основным недостатком является то, что обычно существует большое пространство для данных. Многие предполагают, что существует также высокий накладные расходы для вставки или извлечения новых матриц, но на самом деле есть несколько документированных методов, которые могут сделать это достаточно быстро.
ваша матрица плотности разреженные? Если он разрежен, для каждой записи может быть лучше просто сохранить список хитов, а не иметь полную 2D-таблицу, которая в основном равна 0.
вместо двух таблиц я бы просто использовал одну таблицу: (x, y, результат). Кроме того, трудно дать больше советов с ограниченной информацией.
видеопамять, очень простая 2D матрица хранится следующим образом:
в ОЗУ последовательно, как массив as
элемент x, y можно найти при смещении массива
например, x=2, y=2 (на основе нуля) относится к элементу K.
[y*width+x]=[2*4+2]=10. элемент массива 10 (опять же нулевой) = K, так что вы хорошо.
хранение в списке с разделителями-запятыми позволит вам поместить матрицу любого размера в поле nvarchar. Это предполагает, что вам не нужно запрашивать отдельные ячейки в SQL, но просто возьмите матрицу в целом и обработайте ее на стороне клиента.
ваш стол может выглядеть так:
кроме того, это работает очень хорошо, если вы матрицы разрежены, иначе вы получите много пустых. элементов. Впрочем, это тоже можно обойти.
Как в MySQL хранить большую трехмерную матрицу?
Необходимо создать базу данных MySQL, которая будет хранить матрицу с большой шириной и большой высотой (размеры известны заранее и не меняются). Чтобы в каждой ее ячейке хранилось несколько (во всех ячейках одинаково) чисел. И чтобы пользователь мог быстро считать/записать любое число по его координатам и номеру в кортеже.
Как такое обычно реализуют?
![]()
Знаете кого-то, кто может ответить? Поделитесь ссылкой на этот вопрос по почте, через Твиттер или Facebook.
Посмотрите другие вопросы с метками mysql база-данных матрицы структуры-данных таблицы или задайте свой вопрос.
Site design / logo © 2022 Stack Exchange Inc; user contributions licensed under cc by-sa. rev 2022.6.10.42345
Нажимая «Принять все файлы cookie», вы соглашаетесь, что Stack Exchange может хранить файлы cookie на вашем устройстве и раскрывать информацию в соответствии с нашей Политикой в отношении файлов cookie.
MySQL как лучше хранить матрицу
Доброго времени суток! Подскажите пожалуйста, как лучше хранить двумерный массив? Суть в том, что у меня в базе должны хранится карты высот. Каждая карта представляет собой двумерный массив размерностью 720*720.
Я почитал советы — некоторые предлагают для хранения массива использовать отдельную таблицу. Но у меня таких записей будет порядка 5000 штук. Как-то наверное много таблиц получится.
Конечно самый простой вариант хранить данные в тексте. Но парсинг текста требует много времени. Может кто еще что посоветует?
Заранее огромное спасибо!

Решить это можно только отталкиваясь от того какие и как ты будешь запрашивать данные, и как их обрабатывать.
В MySQL как не храни — будет костыль.
Настоящие СУБД умеют тип данных массив:

Спасибо большое за ответ! В базе хранится дата и матрица. Пользователь запрашивает карту за определенную дату. Т.е. за раз будет запрашиваться только один массив.

Спасибо большое за ответ! К сожалению задание нужно реализовать на SQlite
Ну так SQlite это даже не MySQL. Тогда пили таблицу:
[id], [matrix_id], [X], [Y], [value]
и храни всех свои массивы в одной таблице, выбирай по matrix_id и получишь значения только для нужной тебе матрица. А данные пусть там хранятся, как им угодно.

Интересная идея, сейчас попробую реализовать. Спасибо огромное!
Пользователь запрашивает карту за определенную дату. Т.е. за раз будет запрашиваться только один массив.

Как вы любите придумывать всякую байду — я просто поражаюсь вашей сообразительности.
Берёшь сишку и дампишь свои 5000*720*720 в файлец, тебе даже индекс не нужен, потом читаешь за 1сискол. Это а) в мильён раз быстрее твоей любой бд, б) в тысячи раз проще/надёжней. в) не нужно пилить стопицот кастылей для такого ущербства, как db.
А теперь подумай, что является лучшим выбором: три строчки на сишке + сискол, либо хренпоймичто какая-то бд+стопицот тысяч строк.
5000*720*720 это около 2,4 Гб 🙂 Я понимаю память дешевая, но слышать такие советы от человека, который предлагает быстрый, минимальный си как-то даже не смешно 🙂

Хм, а в бд они будут занимать ещё больше места. Если ты говоришь про оперативу — перечитай мою месагу и укажи где там говорится про оперативу.
Читаешь не весь файл, если ты об этом подумал, а по оффсету(man read(), lseek(), etc), который ты можешь вычислить без индекса. Читаешь ты ровно 720*720, что требует 720*720 оперативы( что является минимум, меньше которого без тормазов ты не получишь нигде).
Читаешь не весь файл, если ты об этом подумал, а по оффсету(man read(), lseek(), etc), который ты можешь вычислить без индекса.
Поясни человеку, зачем ему заново писать то, что давно реализовано в самых примитивных СУБД в сто раз лучше? Кроме того, надо заранее закладывать возможно безболезненно добавить фичи. Завтра он захочет найти среди своих карт высот какие-то определённые точки — что ж ему, на сишечке опять изобретать то, что даже sqlite умеет? ))
Непонятно каким боком тут скулайт. Положи все матрицы в разные файлы двоичным потоком в максимально естественном формате и не парься.

В сто раз лучше? Это тебе в школе рассказали?
Даже 10% перфоманса моих 3-х строк твоя самая лучшая субд не даст, поэтому с этим ты можешь только соседям по парте пристовать.
Да, напишет на сишке, ибо это займёт у него минут 5 времени и 1000% перфоманса скулайта, а на чтение мана скулайта он потратит полчаса, плюс запилить надо + разобрать выхлоп скулайта, что отнимит у него минимум час.
Поэтому, не рассказывай мне про свои анскильношаблоннные предрассудки из детсада, а говори что-то поделу.
Обычно оп видит задачу далеко и может сам понять надо ему скуль или нет. Но он сюда не за этим пришел. А алгоритмы произвольного доступа к записи в файле есть в начале любой книжки по сям/паскалю, не надо мистичности нагнетать на доступ по индексу.
А еще он потратит время на конверсии скулайт -> си-значение, так бережно сэкономленное на парсинге текста 🙂
Скуль тут вообще ни к месту, план натуральный, индекс естественный, сортировки нет.

Угу, я на это указал вот тут: «разобрать выхлоп скулайта».
Ну это ООП головного мозга и вера в скулайт.

Поддерживаю. Тут еще можно будет кеширование в памяти или mmap использовать для полной оптимизации.

Ты толком не описал структуру данных для одной записи. Думаю там координаты вообще хранить не надо. Х=i / row_size, Y=i % row_size. Где i — порядковый номер записи.
Вроде как человеку нужен одновременный доступ к 5000 координат (или неодновременный; ТС кстати не пояснил эту деталь). Так что пусть думает сам 🙂 Но твое решение тоже неидеально, хотя и имеет массу приемуществ.
Тем не менее, мапить файл рано или поздно придется, когда внезапно понадобиться 50 000 или 100 000 координат. А мапинг уже не один сискол 🙂


Вроде как человеку нужен одновременный доступ к 5000 координат (или неодновременный; ТС кстати не пояснил эту деталь). Так что пусть думает сам 🙂 Но твое решение тоже неидеально, хотя и имеет массу приемуществ.
Без разницы какой, хоть 100500ременный. Оно идеально, ибо лучше не запилить.
Тем не менее, мапить файл рано или поздно придется, когда внезапно понадобиться 50 000 или 100 000 координат. А мапинг уже не один сискол 🙂
Не имеет смысла, хоть там мильярд координат, да и на этом загнётся бд.
Распреденная БД не загнется

Ну работать будет да, отдавая по 100мапов в секунду — это не есть вменяемая работа.
Ну тут либо шашечки, либо ехать, хоть как-то. А вообщея с твоей мыслью согласен. Модель данных у ТСа не реляционная, забивать гвозди микроскопом причин не вижу.
Без разницы какой, хоть 100500ременный.
Ну ты тролль. Еще раз 5000 * 720 * 720

Засунь каждую карту в отдельный файл. Так будет со всех сторон проще.

От блин нахрен, у меня есть десяток теребай, а у него нет — ну да.
Ещё раз, если ты не осилил read() и lseek() — это твои проблемы. Читает он 720 * 720, хоть 100500гигов у тебя будь.
В любом случае у тебя будет занимать это 5000 * 720 * 720, что ты мне этим хочешь сказать?

Засунь каждую карту в отдельный файл. Так будет со всех сторон проще.
По реализации в коде может и проще, но тогда автор получит 5000 файлов. Нафига это нужно? Лучше уж либо read + seek заюзать, либо BLOB в SQLite, чтобы все данные в один файл слить.
Ключевое слово BLOB. BLOB это потоковое значение, фактически файл.
1. По себе людей не судят.
2. Я говорил про ОЗУ, а не место на МЖД.

2. Я говорил про ОЗУ, а не место на МЖД.
А причем тут ОЗУ? Как в моём описании в ОЗУ появится 2.4гига — это лишь в твоих мечтах
НЖМД если так уж охота выпендриться.
Ты правда не понимаешь, что файл можно читать не с начала и до обеда, а с любого места по любое? Или ты решил рассмотреть гипотетическую ситуацию загрузки вообще всех матриц в память одновременно, и уверен, что БД тебя в этом случае магически спасет?
Тем не менее, мапить файл рано или поздно придется, когда внезапно понадобиться 50 000 или 100 000 координат
Лол, просто девелопмент не для тебя, братиш.

Лучше бы ты кресты так рекламировал, а то у меня уже отвращение к голому си появляется из-за адептов.
Старая BDB не сможет дать такой throughput, т.к. не может синкать отдельные записи. А без синка база обречена внезапную смерть. А с синком будут ощутимые тормоза (только по сравнению с обычными файлами, естественно). От синка данных может спасти журнал, который в новых версиях, но тащить этого оракловского монстрика ради записей в файле, я делаю хм.
Если запись редкая, а чтение частое, то стандартная и везде в наличии BDB 1.85/1.86 на BTREE или RECNO может быть очень хорошим решением.

Это будет последние, что я сделаю в своей жизни.
А что с адептами нитак? Реальные адепты сишки просто не любят юзать 10к строк на то, что можно сделать 3-мя.

автор получит 5000 файлов. Нафига это нужно?
1) экономия на спичках. Что такого в 5тыщ файлов?
2) гораздо проще для обновления. У тебя имя файла это нужная дата.
В общем, не надо все данные в один файл сливать.
Ломаются и тормозят файловые системы вроде нтфс, а также переполнение глоббинга в shell со товарищи. Можно поделить на директории по тыще штук, тогда везде будет ок.

реальные адепты не будут с пеной у рта доказывать что-то недоучившимся и людям в процессе обучения, а тихо-мирно подскажут направление и все, посадив семя знаний и наблюдая как растет ЧСВчеловек. А тремя и на баше можно писать.
2ТС: Я бы тоже в файле сделал, так как БД, по мнению моей логики следует пихать для списков всяких. Но, возможно, я не прав — учусь сам


а также переполнение глоббинга в shell со товарищи
Это уже давно не актуально.
Можно поделить на директории по тыще штук, тогда везде будет ок.
Здравая мысль. Причём, можно разбить по дням/месяцам и получится что-то типа индекса. Заодно можно будет удобно удалять старые данные.

Дак я сказал нормально, что я не вижу смысла в том, что писали до меня.
А уже тот спор поднял не я, а всякие доказыватели мне их ООП истин, поэтому зачем ты на меня гонишь? Я лишь написал объективно самое простое, быстрое и надёжное решение.
Нинай, у меня греп вот что выдает:
А вот здесь почти везде счет идет на десятки килобайт. Хотя в рамках задачи это не актуально, согласен.

Причём, можно разбить по дням/месяцам и получится что-то типа индекса. Заодно можно будет удобно удалять старые данные.
Но зачем городить такой велосипед если есть SQLite? Табличка с матрицами + сколько душе угодно табличек с метаданными (если и когда будут нужны) и не нужно заморачиваться с созданием папок, подсчётом количества файлов в папке и разруливанием проблем с файловыми системами, если таковые появятся (а с файлами в несколько десятков гигабайт вроде все ФС легко справляются).

разруливанием проблем с файловыми системами, если таковые появятся
о каких таких мифических проблемах вы все говорите? Кстати, а sqlite вообще repair database есть?


о каких таких мифических проблемах вы все говорите?
1) Фрагментация из-за большого кол-ва мелких файлов. Как результат — замедление скорости доступа к данным на HDD накопителях (тут всё зависит от конкретной ФС и её особенностей).
2) Некоторые ФС плохо работают с большим кол-вом небольших файлов, т.к. дописывают кучу метаинформации. На ЛОРе были даже были темы про это (искать лень, было год или полтора назад вроде). Получим оверхед по размеру данных пропорционально количеству файлов.
3) Придётся писать свой велосипед, пусть и небольшой. А, следовательно, искать и править в нём баги. В случае использование элементарного SQLite часть багов за нас уже выловлена и пофикшена (особенно учитывая то, что Firefox юзает SQLite, а, следовательно, «тестеров» у SQLite более чем достаточно). Лично мне лень тратить своё время на решение данной задачи. Зачем? Есть уже готовое решение, да ещё и протестированное.
Кстати, а sqlite вообще repair database есть?
Если я правильно тебя понял, то предлагается делать это через .dump. Примерно так: http://www.ibiblio.org/elemental/howto/sqlite-backup.html
Если я тебя неправильно понял, то поясни, что ты имел ввиду под repair database.

1) а база данных, стало быть, не будет фрагментироваться? А ничего что она тоже файл?
2) «некоторые ФС плохо работают с большим кол-вом небольших файлов» — ты что, издеваешься? Ну не используй эти «некоторые ФС». Или тебя насильно заставляют ставить какой-нить фат16? Все основные ФС отлично работают с 5тыщ файлов. В продакшене я следующие ФС видел/использовал: рейзер3, xfs, ext2, ext3, ext4, jfs, tmpfs.
3) Путь ТС сам выбирает как ему удобнее. Но вот у меня нет никаких проблем написать «велосипед» из 10 строчек:
Если я правильно тебя понял, то предлагается делать это через .dump.
В том-то и дело что ты говоришь про «ненадёжность фс», а сам никогда не восстанавливал битую sqlite-базу.

1) а база данных, стало быть, не будет фрагментироваться? А ничего что она тоже файл?
Тут я неправильно выразился. В случае с одним файлом — дефрагментация спасёт мир, но если их куча мелких, то данные могут быть размазаны по всему разделу несмотря на профедённую дефрагментацию.
Все основные ФС отлично работают с 5тыщ файлов.
Это сейчас у автора ровно 5к файлов. Но никто не гарантирует, что их не станет больше или меньше (тут ни ты ни я не можем сказать, что будет, т.к. не знаем полностью задачи). Лично моя позиция — лучше не юзать россыпь файлов, т.к. это, потенциально, может доставить проблем.
Путь ТС сам выбирает как ему удобнее.
Согласен. Каждый из нас всёравно выберет то, что ему удобней использовать.

В случае с одним файлом — дефрагментация спасёт мир
Увы, для самой мейнстримовой ФС дефрагментатора вообще нет. А так тут три нюанса:
1) виндовые дефрагментаторы, например, умели в том числе дефрагментировать свободное место.
2) у меня есть сомнения что проблемы производительности вообще актуальны. 1) при данных объёмах всё легко закэшируется в оперативе 2) нам ничего не известно о запросах. Может старые данные будут редко запрашиваться. 3) может там два запроса в день прилетает