Russian Qt Forum
Май 23, 2024, 06:49 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: 1 [2] 3   Вниз
  Печать  
Автор Тема: [РЕШЕНО] QSet, QList, QVector3D/2D, toList() и toSet(). Ошибка  (Прочитано 15612 раз)
kostya2vntu
Гость
« Ответ #15 : Июль 03, 2012, 18:58 »

Код
C++ (Qt)
uint qHash(const QVector3D &val)
{
   float f[3] = { val.x(), val.y(), val.z() };
   uint32 * dummy = (uint32 *) f;
   return dummy[0] ^ dummy[1] ^ dummy[2];
}
 
Так действительно лучше. Только просто xor-ить значения нельзя, надо добавить еще хотя-бы умножение на простые целые - иначе будет одинаковый хеш у всех точек которые лежат на одной прямой, перпендикулярной одной из плоскостей координат.
Код:
return (dummy[0] * A) ^ (dummy[1] * B) ^ (dummy[2] * C);
где А,В,С - некоторые большие разные простые числа.
« Последнее редактирование: Июль 03, 2012, 19:06 от Кoнcтантин » Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #16 : Июль 03, 2012, 19:26 »

Так действительно лучше. Только просто xor-ить значения нельзя, надо добавить еще хотя-бы умножение на простые целые - иначе будет одинаковый хеш у всех точек которые лежат на одной прямой, перпендикулярной одной из плоскостей координат.
Чего это Непонимающий Напр 2 точки на оси X: (1, 0. 0) и (2, 0, 0) хеши явно разные. Наверное Вы имели ввиду что-то типа зеркала, напр (1, 0, 0)(0, 1, 0). Да, можно помножить x, y, z напр на 11, 13, 17, но можно и забить - ну будет больше точек в одной из корзин, зато ключ считаем пошустрее, то на то и выйдет.

Хкш - дело хорошее, но в данной задаче вряд ли к месту если искать "неточное" совпадение (как оно в жизни). Да и по памяти расходен весьма - привыкли шиковать.
Записан
DmitryM
Гость
« Ответ #17 : Июль 03, 2012, 21:23 »

Hешение с сортировкой или std::set более надежно - написать компаратор проблемы нет вообще никакой.
Вот и предъявите пожалуйста, а то ввести отношение порядка на множестве точек не могу.
Записан
kostya2vntu
Гость
« Ответ #18 : Июль 04, 2012, 01:20 »

Так действительно лучше. Только просто xor-ить значения нельзя, надо добавить еще хотя-бы умножение на простые целые - иначе будет одинаковый хеш у всех точек которые лежат на одной прямой, перпендикулярной одной из плоскостей координат.
Чего это Непонимающий Напр 2 точки на оси X: (1, 0. 0) и (2, 0, 0) хеши явно разные. Наверное Вы имели ввиду что-то типа зеркала, напр (1, 0, 0)(0, 1, 0). Да, можно помножить x, y, z напр на 11, 13, 17, но можно и забить - ну будет больше точек в одной из корзин, зато ключ считаем пошустрее, то на то и выйдет.

Хкш - дело хорошее, но в данной задаче вряд ли к месту если искать "неточное" совпадение (как оно в жизни). Да и по памяти расходен весьма - привыкли шиковать.
Точно, ошибся, трудный рабочий день выдался )
Записан
kostya2vntu
Гость
« Ответ #19 : Июль 04, 2012, 01:22 »

Hешение с сортировкой или std::set более надежно - написать компаратор проблемы нет вообще никакой.
Вот и предъявите пожалуйста, а то ввести отношение порядка на множестве точек не могу.
Сначала сравниваем по X, если одинаковые - по Y, если Y тоже равны - по Z ...
Записан
Bepec
Гость
« Ответ #20 : Июль 04, 2012, 06:50 »

Igors - я из ваших рассуждений понял только слово зеркало, да и то в виде нашлёпки на шкаф Веселый
Записан
DmitryM
Гость
« Ответ #21 : Июль 04, 2012, 07:20 »

Сначала сравниваем по X, если одинаковые - по Y, если Y тоже равны - по Z ...
Причем тут равенство? Когда требуется неравенство.

Пример:
(0,0,1) < (1,0,0) или (0,0,1) > (1,0,0)
Записан
kostya2vntu
Гость
« Ответ #22 : Июль 04, 2012, 11:14 »

Сначала сравниваем по X, если одинаковые - по Y, если Y тоже равны - по Z ...
Причем тут равенство? Когда требуется неравенство.

Пример:
(0,0,1) < (1,0,0) или (0,0,1) > (1,0,0)

Функция возвращает true усли a < b
Код
C++ (Qt)
bool comp(QVector3D &a, QVector3D &b) {
   if (a.x() < b.x()) return true;
   if (a.x() > b.x()) return false;
   if (a.y() < y.x()) return true;
   if (a.y() > y.x()) return false;
   return a.z() < b.z();
}
 
Что тут сложного?
« Последнее редактирование: Июль 04, 2012, 11:16 от Кoнcтантин » Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #23 : Июль 04, 2012, 14:24 »

Igors - я из ваших рассуждений понял только слово зеркало, да и то в виде нашлёпки на шкаф Веселый
Ну типа x одной координаты равен y другой, т.е. координаты разные а хеш-код получается одинаковый и тормозит. Случай довольно редкий, можно пренебречь

Код
C++ (Qt)
bool comp(QVector3D &a, QVector3D &b) {
   if (a.x() < b.x()) return true;
   if (a.x() > b.x()) return false;
   if (a.y() < y.x()) return true;
   if (a.y() > y.x()) return false;
   return a.z() < b.z();
}
 
Что тут сложного?
Придираюсь: в приличном обществе const положено писать  Улыбающийся

Сложного конечно ничего, и условие сортировки записано совершенно верно. Ну а дальше-то что? Как будете удалять/фильтровать?
Записан
G-virus
Гость
« Ответ #24 : Июль 04, 2012, 15:31 »

Товарищи, позвольте узнать, по поводу чего тут развилась демагогия, и почему Конфуций-Igors пытается во всех внедрить свою философию?
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #25 : Июль 04, 2012, 16:42 »

Товарищи, позвольте узнать, по поводу чего тут развилась демагогия, и почему Конфуций-Igors пытается во всех внедрить свою философию?
Какая демагогия и что не нравится? Обсуждается как сделать грамотно, как в плане реализации, так и постановки.
Записан
Bepec
Гость
« Ответ #26 : Июль 04, 2012, 16:49 »

G-virus вы некорректны. Тут спокойно и нормально протекает процесс "как сделать лучше".

И если это философия Igors -то такую философию нужно внедрять принудительно.
Записан
DmitryM
Гость
« Ответ #27 : Июль 04, 2012, 19:35 »

Код
C++ (Qt)
bool comp(QVector3D &a, QVector3D &b) {
   if (a.x() < b.x()) return true;
   if (a.x() > b.x()) return false;
   if (a.y() < y.x()) return true;
   if (a.y() > y.x()) return false;
   return a.z() < b.z();
}
 
Что тут сложного?
Придираюсь: в приличном обществе const положено писать  Улыбающийся

Сложного конечно ничего, и условие сортировки записано совершенно верно. Ну а дальше-то что? Как будете удалять/фильтровать?
Возможно правильно вот так:
Код
C++ (Qt)
  if (a.x() < b.x()) return true;
  if (a.x() > b.x()) return false;
  if (a.y() < b.y()) return true;
  if (a.y() > b.y()) return false;
 
Если это так, то получается:
(1, 1.3, 10)<(1,1.301, 100)<...<(1,1.34, 100500) < (1, 1.35, 10)
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #28 : Июль 04, 2012, 20:00 »

Возможно правильно вот так:
Код
C++ (Qt)
  if (a.x() < b.x()) return true;
  if (a.x() > b.x()) return false;
  if (a.y() < b.y()) return true;
  if (a.y() > b.y()) return false;
 
Если это так, то получается:
(1, 1.3, 10)<(1,1.301, 100)<...<(1,1.34, 100500) < (1, 1.35, 10)

Да, это Константин описАлся (y.x() - кто такой y ?) а я и не заметил. Да, транзитивность выполняется, ну и что? Допустим в сортированном массиве имеем (согласно условию сортировки)
Цитировать
(1, 1, 0)
(1, 2, 0)
..
(1.00001, 1, 0)
Расстояние между первой и последней точкой меньше критического, но подряд они не идут, std::remove_if (любимое знатоками STL) ничего не дает
Записан
kostya2vntu
Гость
« Ответ #29 : Июль 04, 2012, 21:50 »

Цитировать
(1, 1, 0)
(1, 2, 0)
..
(1.00001, 1, 0)
Расстояние между первой и последней точкой меньше критического, но подряд они не идут, std::remove_if (любимое знатоками STL) ничего не дает

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

Записан
Страниц: 1 [2] 3   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.146 секунд. Запросов: 19.