【问题标题】:Joining Data Frames by Measured Values with an Error Range通过具有误差范围的测量值连接数据帧
【发布时间】:2016-11-22 22:35:41
【问题描述】:

我正在寻找一种方法来加入(或合并)R 中的两个或多个数据帧,其中包含具有指定误差范围的测量值。这意味着“by”列中的值将是 nnn.nnnn +/- 0.000n。容错限制为该值的 3 e-6 倍。

这是我迄今为止最好的尝试。

newDF <- left_join(P0511_480k, P0511_SF00V, by=c(P0511_480k$m.z == (P0511_SF00V$m.z - 0.000003(P0511_480k$m.z)) : (P0511_SF00V$m.z + 0.000003(P0511_480k$m.z))))

在这个表达式中,我有两个数据框(P0511_480kP0511_SF00V),我想将它们合并到一个名为“m.z”的列中。可接受的值范围是正负“m.z”乘以 0.000003。例如,P0511_480k_subset$m.z = 187.06162 应该匹配 P0511_SF00V_subset$m.z = 187.06155

> dput(head(P0511_480k_subset, 10))
structure(list(m.z = c(187.06162, 203.05652, 215.05668, 217.07224, 
279.05499), Intensity = c(319420.8, 288068.9, 229953, 210107.8, 
180054), Relative = c(100, 90.18, 71.99, 65.78, 56.37), Resolution = c(394956.59, 
415308.31, 387924.91, 437318.31, 410670.91), Baseline = c(2.1, 
1.43, 1.69, 1.73, 3.04), Noise = c(28.03, 27.17, 27.52, 27.58, 
29.37)), .Names = c("m.z", "Intensity", "Relative", "Resolution", 
"Baseline", "Noise"), class = c("tbl_df", "data.frame"), row.names = c(NA, 
-5L))

> dput(head(P0511_SF00V_subset, 10))
structure(list(m.z = c(187.06155, 203.05641, 215.05654, 217.0721
), Intensity = c(1021342.8, 801347.1, 662928.1, 523234.2), Relative = c(100, 
78.46, 64.91, 51.23), Resolution = c(314271.88, 298427.41, 289803.97, 
288163.63), Baseline = c(6.89, 10.47, 9.13, 8.89), Noise = c(40.94, 
45.98, 44.3, 44.01)), .Names = c("m.z", "Intensity", "Relative", 
"Resolution", "Baseline", "Noise"), class = c("tbl_df", "data.frame"
), row.names = c(NA, -4L))

感谢您的建议!我已经尽可能广泛地搜索了帮助文档,但找不到与我需要的示例相近的示例。

非常感谢!

【问题讨论】:

  • 请使用dput()dput(head(df, 20)) 提供您的数据(或其子集)。另外,在进行乘法运算时需要指定*(即使数字在括号前)
  • 查看fuzzyjoin package,它是 dplyr 连接操作的一种变体。
  • 我认为你需要像data.table::foverlaps() 这样的东西,提供数据和预期的输出。
  • 谢谢艾蒂安!用这个“test2

标签: r dplyr


【解决方案1】:

如果您不需要不匹配的行,那么这可以工作。假设这两个数据集是 df1 和 df2。查看 df1 中的 m.z 列,如果它在 df2 的 m.z 列中的任何值的 0.000003 容差范围内,则将 df1 中的该值替换为 df2 中相应的匹配值。然后合并两个数据框。

df1$m.z <- sapply(df1$m.z, function(x)
                 {
                  # First check if the element lies within tolerance limits of any element in df2
                  ifelse(min(abs(df2$m.z - x), na.rm=TRUE) < 0.000003 * x,
                  # If yes, replace that element in df1 with the matching element in df2
                   df2[which.min(abs(df2$m.z - x)),"m.z"], 0)
                 })
df3 <- merge(df1, df2)

【讨论】:

  • 是的,但 sapply 将 m.z 值转换为列表。
  • 所以,我添加了“df1$m.z
  • 我明白了。我同意这会有些混乱,但我会使用 for 循环或 lapply 5 个数据帧。
猜你喜欢
  • 1970-01-01
  • 2019-11-18
  • 2020-03-31
  • 2017-07-21
  • 2020-04-04
  • 2019-11-02
  • 1970-01-01
  • 1970-01-01
  • 2019-05-30
相关资源
最近更新 更多