ranglelinear-interpolation

R-question: How to linear interpolate using na.approx() for wind directions (angles) 355 and 5 make 0 instead of 180


I'm trying to linear interpolate a very large dataframe using the na.approx function. Works very well except for angular data e.g. wind directions. If you linear interpolate e.g. 350 and 10 you would get 180 instead of the correct 0 (north direction) Does anybody know a solution for large interpolation

for example:

df <- c(350,NA,10) df <- df %>% na.approx %>% data.frame()

should be 350 0 10 but results are 350 180 10


Solution

  • This seems closely related to the concept of "circular means," and I think we can use the same approach. Convert your polar coordinate (in this case just an angle, e.g. on the unit circle) to cartesian coordinates, do you interpolation there, and then convert back.

    df <- data.frame(theta = c(350, NA, 10))
    
    df |>
      mutate(x_vec = sin(theta*pi/180), # using (x0,y1) for theta = 0
             y_vec = cos(theta*pi/180)) |>
      select(-theta) |>
      zoo::na.approx() |>
      data.frame() |>
      mutate(theta = round(90 - atan2(y_vec, x_vec)/pi*180) %% 360)
    

    Result. Here, theta is our angle: 350, 0, and 10 degrees

              x_vec     y_vec theta
    1 -1.736482e-01 0.9848078   350
    2 -4.718448e-16 0.9848078     0
    3  1.736482e-01 0.9848078    10