Поиск местоположения при нажатии клавиш, как приложение Apple Weather

Я хотел бы выполнить поиск местоположения, как приложение Apple Weather, которое показывает таблицу потенциальных местоположений при каждом нажатии клавиши. Я отправляю строку ввода пользователя в функцию ниже каждый раз, когда в текстовом поле происходит событие "изменение изменено". Строка, кажется, отправлена ​​правильно, но я не получаю ожидаемый массив меток. Например, "Каштан" возвращает только "Каштан, Иллинойс", но если я наберу "Каштан Привет", я получу четыре элемента: "Маршфилд, Массачусетс", "Уилбрахам, Массачусетс", "Саут-Хэдли, Массачусетс" и "Гринфилд, Массачусетс" ". Затем, набрав "Chesnut Hil", вы получите "Brookline, MA", которого даже не было в списке "Chestnut Hi". Код ниже. Большое спасибо!

func forwardGeocoding(address: String) {
    CLGeocoder().geocodeAddressString(address, completionHandler: { (placemarks, error) in
        if error != nil {
            print(error!)
            return
        }
        var placeName = ""
        var placeCoordinate = ""
        self.placeNames = [] // empty arrays at the start of each geocode result
        self.placeCoordinates = []

        if (placemarks?.count)! > 0 {

            for placemark in placemarks! {

                if placemark.country != "United States" {
                    let city = placemark.locality ?? ""
                    let country = placemark.country ?? ""
                    placeName = "\(city) \(country)"
                } else {
                    let city = placemark.locality ?? ""
                    placeName = "\(city), \(placemark.administrativeArea!)"
                }

                let coordinate = placemark.location?.coordinate
                placeCoordinate = "\(coordinate!.latitude), \(coordinate!.longitude)"
                self.placeNames.append(placeName)
                self.placeCoordinates.append(placeCoordinate)
            }
        }
        self.tableView.reloadData()
    })
}

1 ответ

Решение

Некоторые заметные фрагменты из CLGeocoder документы, акцент добавлен:

Объект геокодера - это единичный объект, который работает с сетевым сервисом для поиска информации о метках для указанного значения координат.


Приложения должны осознавать, как они используют геокодирование. Запросы на геокодирование ограничены по скорости для каждого приложения, поэтому выполнение слишком большого количества запросов за короткий промежуток времени может привести к сбою некоторых запросов.


Компьютер или устройство должны иметь доступ к сети, чтобы объект геокодера мог возвращать подробную информацию о метках

Все это говорит о том, что а) используя CLGeocoder возвращать и уточнять результаты поиска "по мере ввода", вероятно, не будет хорошо, в общем, и б) поэтому, вероятно, это не то, что Apple использует в Weather.

Помните, что Weather не хочет отображать введенные пользователем строки в широту / долготу на земном шаре - он выполняет поиск по списку названий мест. (В частности, список мест, по которым партнеры по прогнозу погоды Apple предоставляют данные.) Если вы хотите искать именно такую ​​информацию, вам понадобится собственный список.

Если вы хотите получать результаты поиска "по мере ввода", вам лучше всего использовать локальную базу данных или, по крайней мере, веб-службу, специально предназначенную для этого использования. Как отмечалось в этом старом ответе, для этого есть множество вариантов: Google предлагает некоторые службы, а GeoNames.org - это бесплатная / открытая опция, которая имеет как веб-службы, так и загружаемые базы данных, которые вы можете встроить в свое приложение.

Если у вас есть такая база данных / служба, вы также захотите подумать о том, как вы ее используете. Например, Вы хотите, чтобы "каштановый привет" нашел Каштановый холм, Пенсильвания или (гипотетически; нет ни одного) Каштан, Гавайи? То, как вы будете обрабатывать строки поиска и превращать их в запросы к базе данных, повлияет на ваши результаты.

Другие вопросы по тегам