【问题标题】:mlr3's task$feature_names is re-ordering variables in R?mlr3 的 task$feature_names 在 R 中重新排序变量?
【发布时间】:2020-07-03 04:13:18
【问题描述】:

所以我的问题是,当我有一个数据框,然后使用mlr3task$feature_names 函数创建一个任务时,它会以字母顺序或(某种)不正确的数字顺序返回变量,而我会喜欢保持特征名称出现在数据框中的顺序。我在下面提供了两个例子来说明我的意思。第一个示例是(有点)数字示例,第二个示例是按字母顺序排列的。

示例 1(数字):

library(mlr3)
# Set Values
n <- 10      # No of rows
p <- 10       # No of cols
e <- rnorm(n) # used for noise
b <- 10      


# Create matrix of values
xValues <- matrix(rnorm(n*p), nrow=n)   # Create matrix wt 3 columns
colnames(xValues)<- paste0(1:p)     # Name columns
df <- data.frame(xValues)               # Create dataframe

# Equation 
y <- (b + b*df$X1 - b*df$X2 + (b*df$X3)*(b*df$X2) + e)     # Equation

# Adding y to df
df$y <- y

# mlr3 TASK
test_T = TaskRegr$new(id = "test", backend = df, target = "y")
test_T$feature_names

所以在上面的示例中,我创建了一些数据(即 X1 到 X11),然后创建了一个 mlr3 任务。但是,当我运行 test_T$feature_names 时,它会返回:

[1] "X1"  "X10" "X2"  "X3"  "X4"  "X5"  "X6"  "X7"  "X8"  "X9" 

所以,由于 X10 中的前导 1,mlr3 认为 X10 应该出现在 X2 之前。

示例 2(按字母顺序):

library(mlr3)
a  <-rnorm(10)
b  <-rnorm(10)
ab <-rnorm(10)
ba <-rnorm(10)
c  <-rnorm(10)
myData <- data.frame(a, b, ab, ba, c)
t_T = TaskRegr$new(id = "test", backend = myData, target = "c")
t_T$feature_names

所以这一次,我的数据框中的变量顺序由myData 描述(即a、b、ab、ba、c)。但是,当我运行 t_T$feature_names 时,它会返回:

[1] "a"  "ab" "b"  "ba"

它已将顺序更改为按字母顺序排列。我不确定这是故意的还是mlr3 的疏忽...但是无论如何从mlr3 创建的任务中提取特征名称,它不会重新排序变量名称?
我还是卡在这个问题上,如果有人有什么建议吗?

编辑:我添加了一个(糟糕的)图形示例,只是为了说明问题。因此,从数字示例继续,如果我想创建一个热图样式图,但使用 $feature_names 获取特征名称,我最终会得到这样的结果:

nam <- test_T$feature_names

var_int2 = df %>% as_tibble %>% 
  mutate(var_num1 = 1:length(nam)) %>% 
  pivot_longer(cols = 1:length(nam),
               values_to = 'values') %>% 
  mutate(var_num2 = rep(1:length(nam), length(nam)),
         alpha_imp = as.integer(var_num1 == var_num2),
         alpha_int = 1 - alpha_imp)

p <- ggplot(data = var_int2, 
            mapping = aes(x = var_num1, y = var_num2)) + 
  scale_x_continuous(breaks = 1:length(nam), labels = nam, position = "top") + 
  scale_y_reverse(breaks = 1:length(nam), labels = nam) +
  geom_raster(aes(fill = y),
              alpha = var_int2$alpha_int)

p

这将产生如下内容:

可以看出,它在 X1 和 X2 之间绘制 X10。理想情况下,我想保持特征出现在数据框中的顺序。我知道可能还有其他方法可以重新排序绘图,但是,我在创建的大型绘图函数中依赖 $feature_names。最初,我使用mlr 中的getTaskFeatureNames(task),它使功能名称保持原始顺序......但我最近更新为mlr3,这似乎改变了顺序。

【问题讨论】:

  • 您能否总结一下最终结果或将其中一个答案标记为已接受?这将有助于未来的读者。谢谢。

标签: r mlr3


【解决方案1】:

如果您能提供一个功能顺序很重要的示例或用例,我们可以尝试保留它。

【讨论】:

【解决方案2】:

我们进行了简短的讨论,不认为这是一个错误。也可以查看任务中的数据,获取列名

task = tsk("mtcars")
task$feature_names
# [1] "am"   "carb" "cyl"  "disp" "drat" "gear" "hp"   "qsec" "vs"   "wt"  
colnames(task$data())
# [1] "mpg"  "am"   "carb" "cyl"  "disp" "drat" "gear" "hp"   "qsec" "vs"   "wt" 

注意,这包含目标列。此外,如果您使用另一个后端然后只使用data.table,它可能会变慢,因为将检索数据,而$feature_names 与数据无关。

综上所述,您可以使用此解决方案的顺序很重要

setdiff(colnames(task$data()), task$target_names)

【讨论】:

  • 感谢您的回复。总而言之,我在包中的一个函数中使用$feature_names 来获取功能名称,然后我用它来创建我设计的一些自定义图。在字母示例中不是很明显,但在数字示例中,我的图按数字顺序(即 X1、X2、...、Xn)是有意义的。目前,它正在 X1 旁边绘制 X10 等。关于您的解决方案,$feature_namessetdiff(colnames(task$data()), task$target_names) 之间没有区别。两者都有相同的输出
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-05-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多