Отображение предметов в 2-мерном пространстве в память - PullRequest
1 голос
/ 06 января 2012

У меня есть количество предметов, которые идентифицируются по его 2-мерным координатам (короткий знак со знаком). Каждый элемент является классом, содержащим 64 КБ данных. Есть около 500-1500 предметов в любой момент. Предметы обычно группируются по ~ 20 вокруг точки. Мой вопрос: как мне их отобразить, чтобы это не занимало слишком много памяти? Элементы будут добавляться / удаляться медленно (1-10 в секунду) и будут выбираться очень часто, поэтому выборка элемента из списка (указатель на большую структуру) должна быть максимально быстрой.

Я пришел к выводу, что существует класс gridContainer с допустим, что он будет хранить прямоугольник с указателями 64x64. У меня будет основной контейнер сетки, в котором будет храниться другой gridContainer, а этот вложенный gridContainer будет хранить фактические элементы, которые я хочу отобразить (это позволит 4096x4096 реальных элементов). Чтобы получить доступ к определенному элементу, например [260, 130], я бы разделил его на 64 и взял бы частное, чтобы найти позицию родительского gridContainer, а остаток - для поиска вложенного положения gridContainer. Так что для [270,145] у меня было бы [4,2] и [14,17].

Я также думал об использовании std::map, но я не знаю его внутренностей и не знаю, какую производительность от него ожидать.

Какие-либо предложения по моему методу или есть лучший способ сделать это?

Ответы [ 3 ]

2 голосов
/ 06 января 2012

Вы можете использовать std :: map, как уже предлагалось, который является просто контейнером дерева ab, или вы можете использовать хеш-таблицу, которая потенциально может быть быстрее.Квадратное дерево также является вариантом, который будет гораздо более сложным, чем предыдущие два варианта, но обеспечит ранние варианты.

Хеш-таблица с минимальной загрузкой имеет хорошие шансы быть поиском O (1), но имеет наихудший случай O (n), когда n = элементы присутствуют.Если вы можете сохранить нагрузку ниже примерно 10%, то вам понадобится действительно ужасная функция хеширования, чтобы стать хуже, чем O (1).Это, очевидно, отнимает много дополнительной памяти, но потенциально может быть самым быстрым вариантом.Тип сравнения для хеш-таблицы довольно сложен.У вас есть хеш-функция, которая принимает ввод типа ключа, в данном случае пару шорт, и возвращает индекс.Этот индекс соответствует местоположению в полуфиксированном массиве объектов.Если там уже есть объект, столкновение должно быть разрешено, что может привести к отрицательному времени выполнения, поэтому чем оно меньше, тем лучше.

У четырехугольного дерева наилучшее время возврата в случае O (1),но только для пустых ячеек, в то время как при наличии элемента он имеет время поиска O (log n), где n - размер требуемого поля.Если у вас мало объектов, это может потреблять больше памяти, чем хеш-таблица, но, как указано выше, вы получите приличное время выполнения и поиск, который не даст результатов, может завершиться с относительной скоростью.Тип сравнения для дерева Quad обычно представляет собой каскадную логическую проверку.

Std :: map имеет постоянное время поиска O (log n), где n - элементы на карте.Это наиболее эффективный для памяти вариант, но он имеет гарантированное время выполнения для любого поиска.Тип сравнения для std :: map - это каскадная операция меньше чем, которая в случае с int ((short1 << 16) | short2) также довольно быстрая. </p>

Хороший обзориз контейнеров, которые вы, вероятно, будете использовать.То, что вы должны использовать, зависит от того, насколько загруженным вы ожидаете, что ваш стол будет.С всего несколькими объектами (<500), std :: map, вероятно, ваш лучший выбор.Для 500 до 5000, вы, вероятно, должны использовать четырехугольное дерево.Более того, вы начнете использовать смешное количество памяти для дерева и, вероятно, должны использовать вместо этого хеш-таблицу. </p>

1 голос
/ 06 января 2012

A Quad Tree , кажется, то, что вы ищете.

1 голос
/ 06 января 2012

Вы всегда можете использовать std::map<std::pair<short, short>, *item>, это позволит получить и добавить за log(n) время, но для более точного ответа мы должны знать, какие операции вам требуются, чтобы быть быстрыми

...