присвоение фактора фрейму данных - PullRequest
2 голосов
/ 13 июня 2011

Я хочу добавить столбец к фрейму данных, который будет кодировать определенные уровни фактора. например

subject  rate
1          12
1          10 
1          13
4          4
4          6
4          12
2          9
2          2
2          5
6          17
6          10
6          1

в приведенном выше кадре данных я хотел бы добавить третий столбец, называемый «лечение», в котором субъектам назначается один из двух уровней «а» или «б». например ниже

subject  rate  treatment
1          12      a
1          10      a
1          13      a
4          4       b
4          6       b
4          12      b
2          9       b
2          2       b
2          5       b 
6          17      a
6          10      a
6          1       a  

Заранее спасибо за любую помощь.

Ответы [ 4 ]

5 голосов
/ 13 июня 2011

Вот еще один подход с использованием пакета plyr:

library(plyr)

#Make some fake data
set.seed(1)
dat <- data.frame(subject = rep(c(1,4,2,6), each = 3), rate = sample(1:20, 12, TRUE))

set.seed(1)
#Assign treatment based on the subject ID. This does not ensure that you will get
#at least one subject in each treatment group.
ddply(dat, "subject", transform, treatment = sample(letters[1:2], TRUE))

РЕДАКТИРОВАТЬ - на ваш комментарий

Учитывая, что вы хотите указать, какому субъекту назначается какое лечение, предложение Гэвина о merge является точным. Сначала я создал бы новый data.frame, который содержит одну запись для каждого уникального субъекта, назначил их обработку, а затем объединил их вместе:

treatments <- data.frame(subject = unique(dat$subject), treats = c("a", "b", "b", "a"))
merge(dat, treatments)

Обратите внимание, что порядок unique(dat$subject) равен 1,4,2,6, что соответствует порядку значений в исходном data.frame. Если ваша реальная проблема содержит более четырех предметов, вы можете рассмотреть более автоматизированный способ назначения групп лечения. Один из подходов, которые я использовал в прошлом, заключается в назначении случайного числа каждому респонденту, а затем в назначении групп на основе заданного порога этого случайного числа. По сути, это то же самое, что и описанный выше подход, но может гарантировать, что вы получите равные числа в каждой группе. Например:

dat <- ddply(dat, "subject", transform, treatment = runif(1))
dat <- within(dat, treatment <- ifelse(treatment < quantile(treatment, 0.5),"a", "b"))
5 голосов
/ 13 июня 2011

Если вы хотите назначить процедуры случайным образом, это сделает это:

## subject IDs
subj <- with(dat, unique(subject))

## how many treatment levels?
ntreat <- 2

## sample an identifier for the treaments
set.seed(47)
treats <- sample(letters[seq_len(ntreat)], length(subj), replace = TRUE)

## stick this into a subject/treatment data frame
Treat <- data.frame(cbind(subject = subj, treatment = treats))

Это дает:

R> Treat
  subject treatment
1       1         b
2       4         a
3       2         b
4       6         b

Edit:

Если процедуры были предварительно назначены, просто создайте кадр данных Treat вручную;

Treat <- data.frame(subject = c(1,4,2,6), treatment = c("a","b","b","a"))

Если у вас есть множество таких функций, вы можете использовать такие функции, как seq() и rep(), а также встроенную постоянную letters для ускорения «ввода данных».

Конец редактирования

Теперь мы можем использовать этот фрейм данных в слиянии с исходными данными, чтобы вставить treatment для соответствующего subject, используя merge():

R> merge(dat, Treat)
   subject rate treatment
1        1   12         b
2        1   10         b
3        1   13         b
4        2    9         b
5        2    2         b
6        2    5         b
7        4    4         a
8        4    6         a
9        4   12         a
10       6   17         b
11       6   10         b
12       6    1         b
2 голосов
/ 13 июня 2011

Я предполагаю, что у вас есть ключ к преобразованию этих данных, например, 1,6 => a, 4,2 => b. Тогда микс ifelse и %in% должен выполнить работу:

df$treatment<-factor(ifelse(df$subject%in%c('1','6'),'a','b'))

Более общий вариант - скопировать этот фактор и изменить его уровни, но детали зависят от того, как хранится ваш словарь. Простой пример:

x<-df$subject; levels(x)<-c('a','b','b','a')
x->df$treatment

(В обоих примерах я предполагаю, что субъект является фактором)

0 голосов
/ 11 июня 2018

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

Вот код:

data <- data.frame(subject = as.numeric(rep(c(1,2,4,6)), each = 4), rate = sample(1:20, 16, TRUE))

cat = function(x){
  if (x == 1 || x == 4){return('a')}
  else if (x == 2 || x == 6 ) {return('b')}
  else { NaN}
}

data$treat = lapply(data$subject, cat)

head(data)

Выход:

> head(data)
  subject rate treat
1       1   15     a
2       2   20     b
3       4    8     a
4       6   16     b
5       1   19     a
6       2    5     b
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...