24

为了复制,我喜欢为每个数据帧保留一个包含元数据的码本。数据码本是:

一个书面或计算机化的列表,对将包含在数据库中的变量提供清晰和全面的描述。 Marczyk 等人2010 年

我喜欢记录变量的以下属性:

  • 姓名
  • 描述(标签、格式、比例等)
  • 来源(例如世界银行)
  • 源媒体(网址和访问日期、CD 和 ISBN,或其他)
  • 磁盘上源数据的文件名(有助于合并码本)
  • 笔记

例如,这是我正在实施的记录数据框mydata1中的变量的方法,其中包含 8 个变量:

code.book.mydata1 <- data.frame(variable.name=c(names(mydata1)),
     label=c("Label 1",
              "State name",
              "Personal identifier",
              "Income per capita, thousand of US$, constant year 2000 prices",
              "Unique id",
              "Calendar year",
              "blah",
              "bah"),
      source=rep("unknown",length(mydata1)),
      source_media=rep("unknown",length(mydata1)),
      filename = rep("unknown",length(mydata1)),
      notes = rep("unknown",length(mydata1))
)

我为我阅读的每个数据集编写了不同的密码本。当我合并数据帧时,我还将合并其相关代码本的相关方面,以记录最终数据库。我通过基本上复制粘贴上面的代码并更改参数来做到这一点。

4

5 回答 5

7

您可以使用该函数将任何特殊属性添加到任何 R 对象attr。例如:

x <- cars
attr(x,"source") <- "Ezekiel, M. (1930) _Methods of Correlation Analysis_.  Wiley."

并查看对象结构中的给定属性:

> str(x)
'data.frame':   50 obs. of  2 variables:
 $ speed: num  4 4 7 7 8 9 10 10 10 11 ...
 $ dist : num  2 10 4 22 16 10 18 26 34 17 ...
 - attr(*, "source")= chr "Ezekiel, M. (1930) _Methods of Correlation Analysis_.  Wiley."

attr并且还可以使用相同的功能加载指定的属性:

> attr(x, "source")
[1] "Ezekiel, M. (1930) _Methods of Correlation Analysis_.  Wiley."

如果您只向数据框添加新案例,则给定属性不会受到影响(请参阅:str(rbind(x,x))而更改结构将删除给定属性(请参阅:)str(cbind(x,x))


更新:基于评论

如果要列出所有非标准属性,请检查以下内容:

setdiff(names(attributes(x)),c("names","row.names","class"))

这将列出所有非标准属性(标准是:名称、row.names、数据框中的类)。

基于此,您可以编写一个简短的函数来列出所有非标准属性以及值。以下确实有效,虽然不是以一种简洁的方式......你可以改进它并组成一个功能:)

首先,定义 uniqe(=非标准)属性:

uniqueattrs <- setdiff(names(attributes(x)),c("names","row.names","class"))

并制作一个包含名称和值的矩阵:

attribs <- matrix(0,0,2)

遍历非标准属性并将名称和值保存在矩阵中:

for (i in 1:length(uniqueattrs)) {
    attribs <- rbind(attribs, c(uniqueattrs[i], attr(x,uniqueattrs[i])))
}

将矩阵转换为数据框并命名列:

attribs <- as.data.frame(attribs)
names(attribs) <- c('name', 'value')

并以任何格式保存,例如:

write.csv(attribs, 'foo.csv')

关于变量标签的问题,请检查read.spsspackage foreign中的函数,因为它完全符合您的需要:将值标签保存在 attrs 部分。主要思想是一个 attr 可以是一个数据框或其他对象,因此您不需要为每个变量创建一个唯一的“attr”,而是只创建一个(例如命名为“变量标签”)并将所有信息保存在那里. 你可以这样称呼:attr(x, "variable.labels")['foo']其中 'foo' 代表所需的变量名。但请查看上面引用的函数以及导入的数据框的属性以获取更多详细信息。

我希望这些可以帮助您以比我上面尝试的更简洁的方式编写所需的函数!:)

于 2011-03-17T00:11:02.570 回答
5

更高级的版本是使用 S4 类。例如,在 bioconductor 中,ExpressionSet用于存储微阵列数据及其相关的实验元数据。

第 4.4 节中描述的 MIAME 对象看起来与您所追求的非常相似:

experimentData <- new("MIAME", name = "Pierre Fermat",
          lab = "Francis Galton Lab", contact = "pfermat@lab.not.exist",
          title = "Smoking-Cancer Experiment", abstract = "An example ExpressionSet",
          url = "www.lab.not.exist", other = list(notes = "Created from text files"))
于 2011-03-17T13:19:03.403 回答
5

comment()功能可能在这里有用。它可以设置和查询对象的注释属性,但具有不被打印的其他正常属性的优点。

dat <- data.frame(A = 1:5, B = 1:5, C = 1:5)
comment(dat$A) <- "Label 1"
comment(dat$B) <- "Label 2"
comment(dat$C) <- "Label 3"
comment(dat) <- "data source is, sampled on 1-Jan-2011"

这使:

> dat
  A B C
1 1 1 1
2 2 2 2
3 3 3 3
4 4 4 4
5 5 5 5
> dat$A
[1] 1 2 3 4 5
> comment(dat$A)
[1] "Label 1"
> comment(dat)
[1] "data source is, sampled on 1-Jan-2011"

合并示例:

> dat2 <- data.frame(D = 1:5)
> comment(dat2$D) <- "Label 4"
> dat3 <- cbind(dat, dat2)
> comment(dat3$D)
[1] "Label 4"

但这会失去对以下内容的评论dat()

> comment(dat3)
NULL

所以这些类型的操作需要明确处理。要真正做你想做的事,你可能需要编写你使用的特殊版本的函数,在提取/合并操作期间维护注释/元数据。或者,您可能希望考虑生成自己的对象类 - 例如作为带有数据框和其他包含元数据的组件的列表。然后为您想要保留元数据的函数编写方法。

沿着这些思路的一个例子是 zoo 包,它为时间序列生成一个列表对象,其中包含保存排序和时间/日期信息等的额外组件,但从子集等的角度来看,它仍然像普通对象一样工作,因为作者已经提供[等功能的方法。

于 2011-03-17T15:25:13.527 回答
4

我如何做到这一点有点不同,而且技术性明显降低。我通常遵循的指导原则是,如果文本不是为了对计算机有意义而只对人类有意义,那么它属于源代码中的注释。

这可能感觉相当“低技术”,但有一些很好的理由这样做:

  • 当其他人将来拿起你的代码时,很明显,注释是明确地供他们阅读的。在数据结构中不寻常的位置设置的参数对于未来的用户可能并不明显。
  • 跟踪抽象对象内部设置的参数需要相当多的纪律。创建代码注释也需要纪律,但没有注释是显而易见的。如果描述是作为对象的一部分进行的,那么查看代码并不会使这一点变得明显。然后代码在“文学编程”这个词的意义上变得不那么“文学”。
  • 在数据对象中携带数据的描述很容易导致描述不正确。例如,如果将包含以 kg 为单位的测量值的列乘以 2.2 以将单位转换为磅,则可能会发生这种情况。很容易忽略更新元数据的需要。

显然,将元数据与对象一起携带有一些真正的优势。如果您的工作流程使上述几点变得不那么密切,那么为您的数据结构创建元数据附件可能会很有意义。我的意图只是分享一些为什么可以考虑基于“低技术”评论的方法的原因。

于 2011-03-17T15:28:44.343 回答
4

截至 2020 年,有直接专用于可能满足您需求的码本的 R 包。

于 2020-02-14T08:47:05.093 回答