R 根据特定范围内的值分配data.table列值

R 根据特定范围内的值分配data.table列值,r,join,merge,data.table,data-manipulation,R,Join,Merge,Data.table,Data Manipulation,所以我有两个数据表 size_categories = data.table(category = c("S", "M", "L"), size_min = c(0, 10, 25), size_max = c(10, 25, Inf), bin = c("blue", "red", "green"))

所以我有两个数据表

    size_categories = data.table(category = c("S", "M", "L"), size_min = c(0, 10, 25), 
                           size_max = c(10, 25, Inf), bin = c("blue", "red", "green"))

    products = data.table(object_id = 1:10, size = seq(1, 37, 4))
我希望合并这些表,以便根据其大小为product表的每一行分配一个bin和size类别

我所知道的笨拙的方法是为产品的每一行指定一个类别,然后合并

products[size >= 0 & size < 10, category := "S"]
products[size >= 10 & size < 25, category := "M"]
products[size >= 25, category := "L"]
merge(products, size_categories)
产品[size>=0&size<10,类别:=“S”]
产品[尺寸>=10,尺寸<25,类别:=“M”]
产品[尺寸>=25,类别:=“L”]
合并(产品、大小和类别)
当然,这一点都不灵活,如果大小和类别发生变化,我将不得不重写它

我愿意使用其他软件包,但更喜欢只使用data.table的解决方案


谢谢

我会使用非等连接:

products[size_categories, `:=`(category = i.category, bin = i.bin),
    on = .(size >= size_min, size < size_max)]
# > products
#     object_id size category   bin
#  1:         1    1        S  blue
#  2:         2    5        S  blue
#  3:         3    9        S  blue
#  4:         4   13        M   red
#  5:         5   17        M   red
#  6:         6   21        M   red
#  7:         7   25        L green
#  8:         8   29        L green
#  9:         9   33        L green
# 10:        10   37        L green
products[size\u categories,`:=`(category=i.category,bin=i.bin),
on=(大小>=大小\最小值,大小<大小\最大值)]
#>产品
#对象id大小类别箱
#1:1蓝色
#2:25 S蓝色
#3:39 S蓝
#4:4 13米红色
#5:517米红色
#6:6 21米红色
#7:725L绿色
#8:829L绿色
#9:933L绿色
#10:1037升绿色

以下是使用
foverlaps
的方法供参考:

foverlaps(setkey(size_categories, size_min, size_max), 
          setkey(products[, size2 := size], size, size2))[, size2 := NULL][]
#     object_id size category size_min size_max   bin
#  1:         1    1        S        0       10  blue
#  2:         2    5        S        0       10  blue
#  3:         3    9        S        0       10  blue
#  4:         4   13        M       10       25   red
#  5:         5   17        M       10       25   red
#  6:         6   21        M       10       25   red
#  7:         7   25        M       10       25   red
#  8:         7   25        L       25      Inf green
#  9:         8   29        L       25      Inf green
# 10:         9   33        L       25      Inf green
# 11:        10   37        L       25      Inf green

如果“size_categories”表中有更多列需要包含在最终输出中,这可能会有所帮助。

还有
foverlaps
,但我认为这需要复制一列并设置键+非常感谢!假设size_类别有更多的列,我想保留其中的大部分。我是否需要以类似的方式列出它们,还是有更快的方法?@paxton在这种情况下,连接比就地修改更合适。我希望我之前对类似问题的回答中的示例会有所帮助: