3

我对 R 还是很陌生,最近遇到了一些我不确定它是什么意思的东西。data.frame并且data.table有相同的类型?一个对象可以有多种类型吗?将“汽车”从 转换data.frame为 后data.table,我显然无法应用适用于data.frames和不适用的功能data.table,但class()显示“汽车”仍然是data.frame. 有谁知道为什么?

> class(cars)
[1] "data.frame"
> cars<-data.table(cars)
> class(cars)
[1] "data.table" "data.frame"
4

2 回答 2

6

目前尚不清楚您所说的“我显然无法应用适用于 data.frames 而不是 data.table 的函数”是什么意思。

许多函数都按您的预期工作,无论是应用于 adata.frame还是应用于 a data.table。特别是,如果您阅读 的帮助页面?data.table,您会在描述的第一段中找到这一特定行:

由于 adata.table a ,因此它与接受data.frame的 R 函数和包兼容。onlydata.frame

你可以自己测试一下:

library(data.table)
CARS <- data.table(cars)

以下都应该给你相同的结果。它们不是“data.table”的做事方式,但我刚刚从头顶弹出了一些东西,向您展示许多(大多数?)功能可以以与data.table您相同的方式使用会与它们一起使用data.frame(但那时,您会错过所有data.table必须提供的好东西)。

with(cars, tapply(dist, speed, FUN = mean))
with(CARS, tapply(dist, speed, FUN = mean))
aggregate(dist ~ speed, cars, as.vector)
aggregate(dist ~ speed, CARS, as.vector)
colSums(cars)
colSums(CARS)
as.matrix(cars)
as.matrix(CARS)
t(cars)
t(CARS)
table(cut(cars$speed, breaks=3), cut(cars$dist, breaks=5))
table(cut(CARS$speed, breaks=3), cut(CARS$dist, breaks=5))
cars[cars$speed == 4, ]
CARS[CARS$speed == 4, ]

但是,在某些情况下这不起作用。相比:

cars[cars$speed == 4, 1]
CARS[CARS$speed == 4, 1]

为了更好地理解这一点,我建议阅读常见问题解答。特别是,在这个问题上总结了几个相关点:你可以用 data.frame 做什么,而你不能在 data.table 中做


如果您的问题是,更一般地说,“一个对象可以有多个类吗?”那么您已经从自己的探索中看到,是的,它可以。有关这方面的更多信息,您可以从 Hadley 的 devtools wiki 阅读此页面


类还影响诸如对象如何打印以及它们如何与其他函数交互等事情。

考虑rle函数。如果你看一下class,它会返回“rle”,如果你看一下它的str结构,它表明它是一个列表。

> x <- rev(rep(6:10, 1:5))
> y <- rle(x)
> x
 [1] 10 10 10 10 10  9  9  9  9  8  8  8  7  7  6
> y
Run Length Encoding
  lengths: int [1:5] 5 4 3 2 1
  values : int [1:5] 10 9 8 7 6
> class(y)
[1] "rle"
> str(y)
List of 2
 $ lengths: int [1:5] 5 4 3 2 1
 $ values : int [1:5] 10 9 8 7 6
 - attr(*, "class")= chr "rle"

由于每个列表项的长度相同,您可能希望可以方便地使用data.frame()将其转换为data.frame. 我们试试看:

> data.frame(y)
Error in as.data.frame.default(x[[i]], optional = TRUE, stringsAsFactors = stringsAsFactors) : 
  cannot coerce class ""rle"" to a data.frame
> unclass(y)
$lengths
[1] 5 4 3 2 1

$values
[1] 10  9  8  7  6

> data.frame(unclass(y))
  lengths values
1       5     10
2       4      9
3       3      8
4       2      7
5       1      6

或者,让我们class向对象添加另一个并尝试:

> class(y) <- c(class(y), "list")
> y ## Printing is not affected
Run Length Encoding
  lengths: int [1:5] 5 4 3 2 1
  values : int [1:5] 10 9 8 7 6
> data.frame(y) ## But interaction with other functions is
  lengths values
1       5     10
2       4      9
3       3      8
4       2      7
5       1      6
于 2013-04-13T09:20:23.160 回答
3

Data.table 和 data.frame 是不同的类,但它们是通过继承关联的。Data.table继承自data.frame,基本扩展了它的能力。您还可以看到将汽车转换为 data.table 类后:

R> typeof(cars)
[1] "list"      # similar to dataframe

R> mode(cars)
[1] "list"      # idem

更多信息在这里或只是谷歌“继承”。

于 2013-04-13T07:29:26.977 回答