2015-03-21 3 views
1

Предположим, у меня есть 1000 объектов с широтой/долготой.Rails Сравнение Широта/Долгота

Что бы я хотел сделать, это отправить широту/долготу пользователя и вернуть 50 ближайших объектов. Я знаю, как я мог бы сделать это с одним значением - если бы у меня была только широта, но расположение кажется другим с двумя значениями, поэтому я не уверен, как это сделать.

Что было бы лучшим способом добиться этого? Не стесняйтесь указывать мне учебник или что-то еще - я очень новичок в использовании места в рельсах :).

+0

проверить https://github.com/geokit/geokit-rails –

+2

также проверить геокодер: https://github.com/alexreisner/geocoder – srecnig

+0

Драгоценный камень геокодера является выдающимся. Если вы посмотрите журналы выполнения, вы увидите, как ваш простой вопрос переводится в некоторые расширенные вычисления, такие как ... [1m [36mLocation Load (93.8ms) [0m [1mSELECT местоположения. *, 3958.755864232 * 2 * ASIN (SQRT (POWER (SIN ((30.267153 - location.latitude) * PI()/180/2), 2) + COS (30.267153 * PI()/180) * COS (location.latitude * PI()/180) * POWER (SIN ((- 97.7430608 - location.longitude) * PI()/180/2), 2))) AS distance, MOD (CAST ((ATAN2 (((location.longitude - -97.7430608)/57.2957795), ((местоположения .latitude - 30.267153)/57.2957795)) * 57.2957795) ... – Elvn

ответ

1

В исходном вопросе о представлении данных нет деталей, но давайте предположим, что у вас есть список значений lat/long в форме, [lat, long] в списке, locations. Предположим, что у вас есть метрический метод для расстояния между ними, dist(lat, long).

Тогда это будет собрать все комбинации пара расположения и их соответствующих расстояний как совокупность троек, [dist, p1, p2]:

location.combination(2).collect { |p| [dist(p[0], p[1]), p[0], p[1]] } 

Вы можете отсортировать этот который закажет расстояние, и обрывать топ-50 :

location.combination(2).collect { |p| [dist(p[0], p[1]), p[0], p[1]] }.sort.first(50) 

Вы должны были бы увидеть, если он работает с 1000 объектов, так как это создаст 999,000 комбинации первоначально и я не знаю, что емкость массива Руби.

+0

Это замечательно - на самом деле я еще не написал ни одного кода, просто разработав дизайн в своем уме. Я думаю, что это определенно может быть жизнеспособным вариантом. По крайней мере, поставив меня на правильный путь! –

+0

@TomHammond Я надеюсь, что это поможет. Если количество объектов окажется слишком большим, тогда данные нужно будет разделить на более мелкие группы и сделать по кусочкам. – lurker

+1

Полностью делает. Очень ценю вашу помощь! –

1

Это классическая проблема компьютерных наук, называемая nearest neighbor problem. См. Это wikipedia article для двух популярных решений.

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

+0

Это правда в большинстве случаев. Однако, имея дело с эллипсоидной землей, координаты не ведут себя как прямые. Иногда ближайший сосед может быть близок с точки зрения «числа», но может быть над северным полюсом, а не прямым выстрелом, и будут работать только реальные географические расчеты. – courtsimas

Смежные вопросы