Создайте векторную длину списка исходных векторов такой же длины, что и исходный вектор. - PullRequest
5 голосов
/ 29 августа 2011

Эта проблема кажется тривиальной, но я нахожусь в конце концов после нескольких часов чтения.

Мне нужно сгенерировать вектор такой же длины, что и входной вектор, который перечисляет для каждого значения входного вектора общее количество для этого значения. Итак, в качестве примера, я бы хотел сгенерировать последний столбец этого фрейма данных:

> df
   customer.id transaction.count total.transactions
1            1                 1                  4
2            1                 2                  4
3            1                 3                  4
4            1                 4                  4
5            2                 1                  2
6            2                 2                  2
7            3                 1                  3
8            3                 2                  3
9            3                 3                  3
10           4                 1                  1

Я понимаю, что это можно сделать двумя способами: либо с использованием длин серий первого столбца, либо сгруппировав второй столбец с использованием первого и применив максимум.

Я пробовал оба варианта:

> tapply(df$transaction.count, df$customer.id, max)

И рле:

> rle(df$customer.id)

Но оба возвращают вектор более короткой длины, чем оригинал:

[1] 4  2  3  1

Любая помощь с благодарностью принята!

Ответы [ 3 ]

6 голосов
/ 29 августа 2011

Вы можете сделать это без создания счетчика транзакций с помощью:

df$total.transactions <- with( df,  
                     ave( transaction.count , customer.id , FUN=length) )
1 голос
/ 29 августа 2011

Вы можете использовать rle с rep, чтобы получить то, что вы хотите:

x <- rep(1:4, 4:1)
> x
 [1] 1 1 1 1 2 2 2 3 3 4

rep(rle(x)$lengths, rle(x)$lengths)
> rep(rle(x)$lengths, rle(x)$lengths)
 [1] 4 4 4 4 3 3 3 2 2 1

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

Или, как предложил Карстен с ddply из plyr:

require(plyr)

#Expects data.frame
dat <- data.frame(x = rep(1:4, 4:1))
ddply(dat, "x", transform, total = length(x))
0 голосов
/ 29 августа 2011

Вы, вероятно, ищете подход «разделить-применить-объединить»; взгляните на ddply в пакете plyr или на функцию split в базе R.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...