# Geocoder API

Geocode addresses using the ‘HERE Geocoder’ and ‘HERE Geocoder Autocomplete’ APIs.

## Geocode addresses

In order to geocode addresses, the function `geocode()` is used. The requests are sent asynchronously, which means that every geocoded address is counting as one request. If the option `autocomplete` is set to `TRUE`, the addresses are sent to the ‘Geocoder Autocomplete’ API before geocoding, which improves matches but doubles the amount of requests. The addresses have to be of type `character`:

    head(addresses, 3)
    #> [1] "Luzern"   "Lugano"   "Lausanne"

Geocode the character vector containing the addresses:

    geocoded <- geocode(addresses, autocomplete = FALSE)

The return value is an `sf` object containing `POINT` geometries of the addresses:

    head(geocoded, 3)
    #> Simple feature collection with 3 features and 8 fields
    #> geometry type:  POINT
    #> dimension:      XY
    #> bbox:           xmin: 6.63222 ymin: 46.00297 xmax: 8.95121 ymax: 47.04954
    #> CRS:            EPSG:4326
    #>   id              address postalCode     city       county state country  type
    #> 1  1  Luzern, LU, Schweiz       6003   Luzern Luzern-Stadt    LU     CHE point
    #> 2  2 Lugano, TI, Svizzera       6900   Lugano       Lugano    TI     CHE point
    #> 3  3 Lausanne, VD, Suisse       1003 Lausanne     Lausanne    VD     CHE point
    #>                   geometry
    #> 1 POINT (8.30438 47.04954)
    #> 2 POINT (8.95121 46.00297)
    #> 3 POINT (6.63222 46.51961)

Not found addresses are deleted from the result. This means that the `sf` object may contain fewer rows than the original number of addresses. The column `"id"` matches the order of the the input addresses. Using the `"id"` column a corresponding `data.frame` `"df"` with the addresses to geocode could be joined to the coordinates after geocoding.

    df <- data.frame(
      company = c("Schweizerische Bundesbahnen SBB", "Bahnhof AG", "Deutsche Bahn AG"),
      address = c("Wylerstrasse 123, 3000 Bern 65", "not_an_address", "Potsdamer Platz 2, 10785 Berlin"),
      stringsAsFactors = FALSE
    )
    locs <- geocode(df$address)
    geocoded_sfdf <- st_as_sf(data.frame(locs, df[locs$id, ]))

Print the geocoded addresses on an interactive leaflet map:

    mapview(geocoded,
            label = geocoded$address,
            col.regions = "yellow",
            map.types = c("Esri.WorldTopoMap"),
            legend = FALSE,
            homebutton = FALSE
    )

## Autocomplete addresses

The Geocoder Autocomplete API can be accessed using the `autocomplete()` function. The `results` parameter defines the maximum number of suggestions that should be requested for each address.

    suggestions <- autocomplete(addresses, results = 3)

The return value is a `data.table` containing autocomplete suggestions for the addresses. The variable `id` matches the index of the initial address vector, which was used as input and `order` stores the rank of the suggestion.

    results <- data.table(
      input = addresses[suggestions$id],
      id = suggestions$id,
      rank = suggestions$order,
      suggestion = suggestions$label
    )

input | id | rank | suggestion
--- | --- | --- | ---
Luzern | 1 | 1 | Schweiz, Luzern
Luzern | 1 | 2 | Schweiz, Luzern, Luzern-Stadt, Luzern
Luzern | 1 | 3 | Schweiz, Luzern, Luzern-Stadt
Lugano | 2 | 1 | Svizzera, Lugano
Lugano | 2 | 2 | Svizzera, Lugano, Lugano
Lugano | 2 | 3 | Svizzera, Lugano, Lugano, Lugano

## Reverse geocode POIs

The reverse geocoding feature of the Geocoder API can be accessed using the `reverse_geocode()` function. The function allows to retrieve addresses (`landmarks = FALSE`) or landmarks (`landmarks = TRUE`) near POIs.

    rev_addresses <- reverse_geocode(poi = poi, results = 3, landmarks = FALSE)
    rev_landmarks <- reverse_geocode(poi = poi, results = 3, landmarks = TRUE)

The function returns an `sf` object, containing the suggested addresses or landmark names of the reverse geocoded POIs. The coordinates are different from the initially provided POIs since they represent the locations of the suggested addresses or landmarks.

    m <-
      mapview(poi, alpha.region = 0, col.region = "transparent",
              label = poi$city, cex = 30, layer.name = "POIs",
              map.types = c("Esri.WorldTopoMap"), homebutton = FALSE) +
      mapview(rev_addresses, col.region = "yellow", alpha = 0,
              label = rev_addresses$label, layer.name = "Adresses",
              homebutton = FALSE) +
      mapview(rev_landmarks, col.region = "red", alpha = 0,
              label = rev_landmarks$name, layer.name = "Landmarks",
              homebutton = FALSE)
    m

If no addresses or landmarks are found near a POI, `NULL` for this POI is returned. In this case the rows corresponding to this particular POI are missing and merging the POIs by row is not possible. However, in the returned `sf` object, the column `"id"` matches the rows of the input POIs. The `"id"` column can be used to join the original POIs.

## API Reference

- Autocomplete
- Geocoder
- Reverse Geocoder