R - 根据列名对列组进行标准化,并使用条件值

时间:2016-12-27 20:46:49

标签: r dataframe dplyr

我是R和dplyr的新手(来自pandas / python背景)并且我正在尝试在R中进行更多的数据操作。dplyr语法在我身上真的有了增长但是,按照我当前的数据标准化工作,我无法帮助,但我认为必须有一个更清洁的'这样做的方式"。

我有两个data.frames,第一个有值,我想用来动态标准化第二个子集。然后,我想要平均所有具有相同结尾名称的列,然后按更高/更低的方式对行进行分组和分类。如果这个太不清楚了,我希望代码清除一些东西。

正常化(有效,但很乱?)

> main
  airport location x1.takeoffs x1.landings x2.takeoffs x2.landings x3.takeoffs x3.landings x4.takeoffs x4.landings
1     YYZ     N.A.      301029      300976      291615      291614      259649      259613       40326       40297
2     LHR     U.K.      211013      210983      360456      360389      241972      241964      309509      309495
3     JFK     N.A.      432521      432491      205626      205592     1877087     1877060      865802      865771
4     MUC     E.U.      101023      101011       43562       43509      234134      234071       30110       30087
5     VIE     E.U.      250102      250079      128620      128561      152017      152015     1418485     1418471

> norm
  name counts
1   x1     10
2   x2     20
3   x3     30
4   x4     40

我想要做的是将所有以x1开头的列,并将其除以norm[which(norm$name == "x1"),]$counts,依此类推x2x3 ,和x4

这是我的代码:

mainNorm <- main
for (n in norm$name) {
    mainNorm[grep(n, colnames(mainNorm))] <- main %>%
        select(starts_with(n)) %>%
        mutate_each(funs(. / norm[which(norm$name == n),]$counts))
}

现在我平均所有.takeoffs.landings

mainNorm <- mainNorm %>%
  mutate(avg.takeoff=select(., ends_with(".takeoffs")) %>%
  rowMeans(na.rm=T))
mainNorm <- mainNorm %>%
  mutate(avg.landings=select(., ends_with(".landings")) %>%
  rowMeans(na.rm=T))

基于其他列的最小值/最大值

的动态列分配

最后,我想添加一个新列,该列会查看location个群组,并根据"high"中的值<{1}}分配"low"avg.takeoff

我一直在尝试在另一个问题(R - Assign a value/factor in a data.frame to column conditioned on value(s) of other columns)中提出的rowSums方法,但是我遇到了一些障碍。

> mainNorm %>%
    group_by(location) %>%
    mutate(volume=c("high", "low")[rowSums(select(., avg.takeoff) <1)+1])
Error: Position must be between 0 and n

TL; DR

所以,总之我的问题是:

  1. 围绕for循环有更多dplyr方法吗?如果有帮助,我不会介意meltnorm的数据main吗?
  2. 如何在"low"来电中指定"high"group_by?我猜我是否必须将其传递给自定义函数?
  3. 关于我的第二个问题,我猜这总是一个选择:

    mainNorm %>%
      group_by(location) %>%
      filter(avg.takeoff == min(avg.takeoff)) %>%
      mutate(volume="low")
    

    但是,如果我现在想要处理另一半数据,我必须重复,然后加入这两个表。有没有办法在一次filter电话中执行此操作? (回到功能,我猜?)

    编辑:已检测到的结果

    纳入@ alistair的建议有所帮助,但我仍然不确定最后一部分:分配"high""low"。我想以(某种形式或形式)最终得到的是下表:

    # A tibble: 40 × 9
       airport location  name variable value_norm counts avg.takeoff avg.landings volume
        <fctr>   <fctr> <chr>    <chr>      <dbl>  <int>       <dbl>        <dbl> <fctr>
    1      YYZ     N.A.    x1 takeoffs    30102.9     10   13586.692    13584.873    low
    2      LHR     U.K.    x1 takeoffs    21101.3     10   13731.890    13730.148   high
    3      JFK     N.A.    x1 takeoffs    43252.1     10   34437.000    34435.410   high
    4      MUC     E.U.    x1 takeoffs    10102.3     10    5209.404     5207.773    low
    5      VIE     E.U.    x1 takeoffs    25010.2     10   17992.640    17991.220   high
    6      YYZ     N.A.    x1 landings    30097.6     10   13586.692    13584.873    low
    7      LHR     U.K.    x1 landings    21098.3     10   13731.890    13730.148   high
    8      JFK     N.A.    x1 landings    43249.1     10   34437.000    34435.410   high
    9      MUC     E.U.    x1 landings    10101.1     10    5209.404     5207.773    low
    10     VIE     E.U.    x1 landings    25007.9     10   17992.640    17991.220   high
    # ... with 30 more rows
    

0 个答案:

没有答案