【问题标题】:How to automatically interpolate values for one data frame based on another lookup table/data frame?如何根据另一个查找表/数据框自动插入一个数据框的值?
【发布时间】:2019-06-10 05:33:17
【问题描述】:

我有一个数据框和一个查找表。我想要的是将df_dat$valuedf_lookup$threshold 进行比较。 如果value 属于threshold 范围,则在df_dat 中创建一个新列transfer,使其值为 从df_lookup 中的transfer 列线性插值

library(dplyr)

df_lookup <- tribble(
  ~threshold, ~transfer,
  0,   0,
  100,   15,
  200,   35
)
df_lookup
#> # A tibble: 3 x 2
#>   threshold transfer
#>       <dbl>    <dbl>
#> 1         0        0
#> 2       100       15
#> 3       200       35

df_dat <- tribble(
  ~date, ~value,
  "2009-01-01", 0,
  "2009-01-02", 30,
  "2009-01-06", 105,
  "2009-01-09", 150
)
df_dat
#> # A tibble: 4 x 2
#>   date       value
#>   <chr>      <dbl>
#> 1 2009-01-01     0
#> 2 2009-01-02    30
#> 3 2009-01-06   105
#> 4 2009-01-09   150

我可以像这样手动执行此操作,但想知道是否有基于 df_lookup 表中的值的自动方式?谢谢。

df_dat %>% 
  mutate(transfer = case_when(value > 0 & value < 100 ~ 0 + (value - 0)*(15 - 0)/(100 - 0),
                              value >= 100 & value < 200 ~ 15 + (value - 100)*(35 - 15)/(200 - 100),
                              TRUE ~ 0)
  )
#> # A tibble: 4 x 3
#>   date       value transfer
#>   <chr>      <dbl>    <dbl>
#> 1 2009-01-01     0      0  
#> 2 2009-01-02    30      4.5
#> 3 2009-01-06   105     16  
#> 4 2009-01-09   150     25

【问题讨论】:

    标签: r dplyr data.table interpolation lookup-tables


    【解决方案1】:

    您可以使用approx

    df_dat %>% mutate(transfer = with(df_lookup, approx(threshold, transfer, value))$y)
    ## A tibble: 4 x 3
    #  date       value transfer
    #  <chr>      <dbl>    <dbl>
    #1 2009-01-01     0      0
    #2 2009-01-02    30      4.5
    #3 2009-01-06   105     16
    #4 2009-01-09   150     25
    

    【讨论】:

      【解决方案2】:

      另一个使用roll的选项:

      df_lookup[, m := (transfer - shift(transfer, -1L)) / (threshold - shift(threshold, -1L))]
      
      df_dat[, tx := 
          df_lookup[df_dat, on=c("threshold"="value"), roll=Inf, 
              x.m * (i.value - x.threshold) + x.transfer]
      ]
      

      数据:

      library(data.table)
      df_lookup <- fread("threshold, transfer
      0,   0
      100,   15
      200,   35")
      
      df_dat <- fread('date, value
      "2009-01-01", 0
      "2009-01-02", 30
      "2009-01-06", 105
      "2009-01-09", 150')
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2022-01-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多