首页 > 解决方案 > R中的Kmeans聚类结合data.table包

问题描述

我有一个我希望在其上进行 kmeans 聚类的数据集。

基本上有很多 ReEDSregion,在每个 ReEDSregion 内有很多类(ReEDSregion 1,class 1;ReEDSregion 1,class 2;ReEDSregion 2,class 1,等等)。

我想对每个 ReEDSregion 和类组合(通过 ReEDSregion 和类)的变量“grid_cost”使用 10 个集群进行 kmeans 聚类。
一些 ReEDSregion 和类组合的观测值少于 10 个,因此集群的数量与观测值的数量一样多。我首先为此创建了一个函数:

make_bins <- function (dtbl, nbins) {
  # we only need to cluster if there are more unique values for the grid cost than the number of bins desired
  if (dtbl[,length(unique(grid_cost))] > nbins) {
    bins <- kmeans(dtbl[, grid_cost], nbins)$cluster
  } else {
    unique_vals <- sort(unique(dtbl[, grid_cost]))
    bins <- dtbl[,which(unique_vals==grid_cost)]
  }
  return(bins)
}

然后我使用数据表调用函数:

nbins <- 10
scurve[, bin := make_bins(.SD, nbins), by=c("ReEDSregion", "class")]

但它显示错误:

[.data.table(scurve, , :=(bin, make_bins(.SD, nbins)), by = c("ReEDSregion", :
提供 3 个项目分配给列 'bin 中大小为 7 的第 8 组'。RHS 长度必须为 1(单个值即可)或与 LHS 长度完全匹配。如果您希望“回收”RHS,请明确使用 rep() 以使代码读者清楚这一意图。

这是什么意思?有人能帮我吗?

我的数据表的版本是1.12.2。

标签: rdata.table

解决方案


该错误是由于else您的代码中的一部分,当您的值比 bin 少时。

您可以factor在这种情况下使用:

make_bins <- function (dtbl, nbins) {
  # we only need to cluster if there are more unique values for the grid cost than the number of bins desired
  if (dtbl[,length(unique(grid_cost))] > nbins) {
    bins <- kmeans(dtbl[, grid_cost], nbins)$cluster
  } else {
    bins <- dtbl[,dtbl[,as.numeric(factor(grid_cost))]]
  }
  return(bins)
}

测试mtcars

m <- mtcars
setDT(m)
m[,grid_cost:=wt]

nbins <- 10
m[, bin := make_bins(.SD, nbins),by=c("cyl")]
m

     mpg cyl  disp  hp drat    wt  qsec vs am gear carb grid_cost bin
 1: 21.0   6 160.0 110 3.90 2.620 16.46  0  1    4    4     2.620   1
 2: 21.0   6 160.0 110 3.90 2.875 17.02  0  1    4    4     2.875   3
 3: 22.8   4 108.0  93 3.85 2.320 18.61  1  1    4    1     2.320   2
 4: 21.4   6 258.0 110 3.08 3.215 19.44  1  0    3    1     3.215   4
 5: 18.7   8 360.0 175 3.15 3.440 17.02  0  0    3    2     3.440   7
 6: 18.1   6 225.0 105 2.76 3.460 20.22  1  0    3    1     3.460   6
...

推荐阅读