использование R для сравнения фреймов данных для поиска первого вхождения с df1 $ columnA в df2 $ ColumnB, когда df2 $ ColumnB представляет собой список, разделенный одним пробелом

#r

#r

Вопрос:

У меня есть вопрос относительно фреймов данных в R. Я хочу взять data.frame, dfy, и найти первое вхождение dfy $workerId в dfx $ workers, чтобы создать новый фрейм данных, dfz, копию dfx, которая также содержит первое вхождение dfy $ workerId в dfx $ wokers как dfz $ highestRankingGroup. Это немного сложно, потому что dfx $ workers — это отдельная строка с одним интервалом. Мой первоначальный план состоял в том, чтобы сделать это на Perl, но я хотел бы найти способ работать в R и избежать необходимости записывать во temp. Файлы.

спасибо, что уделили мне время.

 y <- "name,workerId,aptitude  
joe,4,34
steve,5,42 
jon,7,23 
nick,8,122"


x <- "workers,projectScore
1 2 3 8 ,92
1 2 5 9 ,89
3 5 7 ,85  
1 8 9 10 ,82  
4 5 7 8 ,83  
1 3 5 7 8 ,79" 

z <- "name,workerId,aptitude,highestRankingGroup
joe,4,0.34,5
steve,5,0.42,2
jon,7,0.23,3
nick,8,0.122,1"

dfy <- read.csv(textConnection(y), header=TRUE, sep=",", stringsAsFactors=FALSE)  
dfx <- read.csv(textConnection(x), header=TRUE, sep=",", stringsAsFactors=FALSE)  
dfz <- read.csv(textConnection(z), header=TRUE, sep=",", stringsAsFactors=FALSE)
  

Ответ №1:

Сначала добавьте highestRankingGroup столбец в свой набор данных dfx

 dfx$highestRankingGroup <- seq(1, length(dfx$projectScore))
  

Поскольку вы упомянули, perl вы можете сделать знакомую вещь perl и просто разделить workers столбец пробелами. Я объединил разделение с функциями из plyr пакета, с которыми всегда приятно работать.

 library(plyr)
df.l <- dlply(dfx, "projectScore")

f.reshape <- function(x) {
  wrk <- strsplit(x$workers, "\s", perl = TRUE)
  data.frame(worker = wrk[[1]]
             , projectScore = x$projectScore
             , highestRankingGroup = x$highestRankingGroup
             )
}

df.tmp <- ldply(df.l, f.reshape)

df.z1 <- merge(df.tmp, dfy, by.x = "worker", by.y = "workerId")
  

Теперь вам нужно искать максимальные значения в projectScore столбце:

 df.z2 <- ddply(df.z1, "name", function(x) x[x$projectScore == max(x$projectScore), ])
  

Это приводит к:

 R> df.z2
  worker .id projectScore highestRankingGroup  name aptitude
1      4  83           83                   5   joe       34
2      7  85           85                   3   jon       23
3      8  92           92                   1  nick      122
4      5  89           89                   2 steve       42
R> 
  

Вы можете изменить df.z2 фрейм данных в соответствии с вашим личным вкусом. Просто посмотрите на разные шаги и созданные объекты, чтобы увидеть, на каком шаге вводятся разные столбцы и т.д.

Ответ №2:

Прежде чем я начну, я рекомендую вам ознакомиться с ответом @mropa . Этот ответ немного забавен, когда я возился с вашим вопросом. С положительной стороны, это действительно связано с небольшим удовольствием с закрытием функций 😉

По сути, я создаю функцию, которая возвращает две функции.

 updateDFz = function(dfy) {
  ## Create a default dfz matrix
  dfz = dfy
  dfz$HRG = 10000 ## Big max value
  counter = 0
  ## Update the dfz matrix after every row
  update = function(x) {
    counter <<- counter   1
    for(i in seq_along(x)) {
        if(is.element(x[i], dfz$workerId))
           dfz[dfz$workerId == x[i],]$HRG <<- min(dfz[dfz$workerId == x[i],]$HRG, counter)
    }
    return(dfz)
  }
  ## Get the dfz matrix
  getDFz = function()
    return(dfz)
  list(getDFz=getDFz, update=update)
}

f = updateDFz(dfy)
lapply(strsplit(dfx$workers, " "), f$update)
f$getDFz()
  

Как я уже сказал, немного забавно 😉

Комментарии:

1. вау, я взял R месяц назад, чтобы провести предварительный анализ данных, и оказалось, что я собираюсь изучать функциональное программирование!

2. Я получаю по почте пару книг на R, о манипуляциях с данными в R amp; ggplot 2. Что вы порекомендуете?

Ответ №3:

Надеюсь, кто-нибудь найдет это полезным.

 # Recieves a data.frame and a search column
# Returns a data.frame of the first occurances of all unique values of the "search" column

getfirsts <- function(data, searchcol){


rows <- as.data.frame(match(unique(data[[searchcol]]), data[[searchcol]]))  
firsts = data[rows[[1]],]

return(firsts)
}