Существует ли способ получить хэш-код плавания с эпсилоном?

Является ли человек настоящей моделью? Почему вы создаете заголовок с помощью JavaScript, а не XML? Вы можете напрямую связать эту модель с представлением, вам просто нужно использовать метод View bindElement, чтобы сделать это.

12
задан mafu 24 February 2009 в 09:01
поделиться

5 ответов

Это - невозможное предположение, что Вы хотите иметь нормальные свойства хэш-кода/равенства:

  • Если X = Y и Y = Z затем X = Z (транзитивность)
  • Если X = Y затем Y = X (commutivity)
  • X = X для всех X (рефлексивность)

Первое правило является проблемой - потому что, если каждое значение считают "равным" следующему большему представимому числу, Вы заканчиваете со всеми числами, являющимися равным. Например, предположите, что число считают равным другому, они в 0,1:

0 равняется 0.08 0.08, равняется 0.16 0.16, равняется 0.24

=> 0 равняется 0.16 по правилу транзитивности => 0, равняется 0.24 по правилу транзитивности

(и т.д.)

Если Вы игнорируете правило транзитивности, то Вы все еще (по-видимому), хотите, чтобы "равные" значения имели равные хэш-коды. Это эффективно осуществляет правило транзитивности - в вышеупомянутом примере, 0 и 0.08 должны иметь равные хэш-коды, также, как и 0 и 0.16. Поэтому 0 и 0.16 должны иметь равные хэш-коды, и так далее. Поэтому у Вас не может быть полезного хэш-кода - это должна быть константа.

14
ответ дан 2 December 2019 в 04:17
поделиться

Все корректны...

ОДНАКО одна вещь, которая часто делается, состоит в том, чтобы расширить понятие хеша немного. Рассмотрите раздел своего 3-го пространства с полями со стороной>> эпсилон.

Хеш точки является полем, которому он принадлежит. Когда Вы хотите к поиску для точки, Вы не проверяете на точку с соответствующим полем (как Вы сделали бы для регулярного хеша), но для соседних полей также. В 3-м необходимо сойти с рук макс. 8 полей.

4
ответ дан 2 December 2019 в 04:17
поделиться

Я не думаю, что у Вас может быть хэш-код, который согласовывается с Вашим методом сравнения, потому что последний не является переходным: для любых трех векторов A, B, C, если A.Equals(B) и B.Equals(C) верны, это могло все еще иметь место это A.Equals(C) ложь. (Вообразите, является ли расстояние между A и B 6e-6 между B, и C является 6e-6, и между A, и C является 1.2e-5), Но равенство хэш-кодов является всегда переходным, так как они - просто числа.

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

8
ответ дан 2 December 2019 в 04:17
поделиться

Я боюсь, что это не находится в общем случае. Эскиз доказательства идет как это:

Возьмите любые два числа a и b. Позвольте различию между ними быть d. Затем при создании d/epsilon чисел с промежуточным шагом эпсилона каждый шаг должен быть "равен" шагу прежде, которые семантикой хэш-кода имеют тот же хэш-код. Таким образом, все числа должны иметь тот же хэш-код.

Можно только решить эту проблему, если Вы добавляете некоторое другое ограничение.

Как в стороне, Вы, которым Равняется определение, неправы также, поскольку это может быть верно, что это a. Равняется (b) и b. Равняется (c), но не a. Равняется (c), который является неправильным при, равняется. Это известно как повреждение свойства Transitivity.

Что я могу сделать затем?

Решение зависит от того, для чего Вы используете хеш. Одно решение состояло бы в том, чтобы представить концептуальную сетку. Измените равняние и хэш-код, таким образом, два количества равны, если в том же кубе сетки, путем округления к постоянному количеству десятичных разрядов, то взятие равняется и хэш-код на округленном числе. Будучи близко к нулю является важным случаем, добавьте смещение эпсилона/2 перед округлением, таким образом, нуль является центром куба. Это корректно, но у Вас может быть два числа произвольно близко друг к другу (под пределами плавания), не будучи равными. Таким образом для некоторых приложений это будет в порядке, другие, которыми это не будет. Это подобно идее от mghie.

7
ответ дан 2 December 2019 в 04:17
поделиться

Независимо от того, что техника, которую Вы используете, будет иметь проблемы, потому что Вы изложили что-то, что не возможно решить.

То, что Вы хотите, 1) равномерно распределяется хеш, таким образом это для большинства чисел a и b где a! = b затем a. GetHashCode ()! = b. GetHashCode (), но 2) где == b затем a. GetHashCode () == b. GetHashCode () должен быть верным.

Возврат константы выполняет (2), но не (1).

Можно продемонстрировать, что округление на 1E-5 границах и использование, что, поскольку хеш нарушает, выполняют (1), но нарушают (2). Возьмите 1E-5 и 2E-5, например. Округление произвело бы два различных значения хэш-функции, но они выдерживают сравнение равный. Это нарушает ограничение (2) выше. Можно легко обобщить это, чтобы доказать, что любое округление числа столкнется с подобной проблемой.

Я рекомендую выбрать другой подход. Я предполагаю, что базовая проблема определяет, ли некоторая точка близко к точке, Вы уже имеете. Я рекомендую рекурсивно разделить координатное пространство пополам (где точки вдоль границы (т.е. <=1E-5 от границы) в обеих половинах). При прогрессивном делении Вас пространство (думайте двоичное дерево), можно создать структуру данных, которая быстро возвратит результат, который Вы хотите и довольно легки создать.

Если я пропустил свое предположение, и необходимо использовать хеш, затем может сделать то, что Вы хотите с двумя значениями хэш-функции каждое округление к 1E-5, но смещение 5E-6. Все равные точки выдержат сравнение равный на одном из этих двух значений хэш-функции. Это потребовало бы, чтобы Вы ввели точку в хеш-таблицу дважды, однажды для каждой стандартной программы хеша.

2
ответ дан 2 December 2019 в 04:17
поделиться
Другие вопросы по тегам:

Похожие вопросы: