2016-01-07 1 views
0

Продолжение на этот вопрос: Add row in R dataframe by unique factor in column showing percent change by MonthУпорядочивание списка по элементу в списке и удалить указанные строки в списке

testing <- data.frame(
    MONTH = c("MTD: 12", "MTD: 12", "MTD: 11", "MTD: 12", "MTD: 12", "MTD: 12"), 
    YEAR = c(2012, 2013, 2014, 2015, 2013, 2014), 
    Client = c("A.", "A.", "A.", "B.", "B.", "B."), 
    Revenue = c(320, 205, 166L, 152, 150, 138), 
    Col1 = c(651, 485, 533, 3932, 171, 436), 
    Col2 = c(478, 335, 305, 238, 115, 251), 
    Col3 = c(73, 69, 57, 6, 67, 57), 
    Col4 = c(6.7, 6.1, 5.5, 6.4, 13.1, 5.5) 
) 

# subset just the month=12 rows 
test12 <- testing[testing$MONTH=="MTD: 12", ] 
test12 <- test12[order(test12$Client, test12$YEAR), ] 

# define a function to calculate percent change 
pctchange <- function(x) { 
    L <- length(x) 
    c(NA, 100 * (x[-1] - x[-L])/x[-L]) 
} 

# calculate percent change for all columns, by client 
change <- apply(test12[, c("Revenue", "Col1", "Col2", "Col3", "Col4")], 2, 
    function(y) unlist(tapply(y, test12$Client, pctchange))) 
change <- data.frame(change) 
names(change) <- paste0("d", names(change)) 
test12b <- cbind(test12[, c("MONTH", "YEAR", "Client")], change) 

# merge back with monthly data 
merge(testing, test12b, all=TRUE) 

Таким образом, после выполнения этого кода вы получите список, который был расщепляется клиентом.

Я хочу запустить следующий код, который будет по существу удалить 2-ю строку, если число строк для этого фактора (клиент) больше чем 2.

Я попытался это уже и не работает:

testing<-ifelse(length(splitresult)>2,splitresult[-2,],splitresult) 

Конечная цель из всего этого:

1) для того, чтобы просто получить процентное изменение в прошлом году с предыдущим годом и не показывают Inbetween вещи, как NA за предыдущий год. Но если это новый клиент, я хочу, чтобы NA там указывал, что это новый клиент. Вот почему я пробовал код выше, который не работал.

2) Я хочу, чтобы изменить порядок клиентов в расколе по доходам в МПД: 12 2014.

splitlist[order(sapply(splitlist, function(x) (x[["Revenue"]])))] 

(Не работает: предположим splitlist это имя списка)

Если любой может помочь мне с любым вопросом, это было бы очень полезно. Благодаря!

+0

Вы пытались использовать пакет 'dplyr'? – Jubbles

+0

У меня нет. Я думаю, мне нужно использовать sapply для второй части вопроса, но не уверен, как это сделать с месяц/год. Я отредактировал вопрос, чтобы показать вам, что я пробовал @Jubbles –

ответ

4

Я думаю, что пакет plyr поможет здесь. Например, вместо последней строки кода, где вы используете ifelse, вы можете попробовать

library(plyr) 
out = ddply(splitresult, "Client", function(x){ 
    if(dim(x)[1] > 2) x = x[-2,] 
    return(x) 
}) 

Здесь x является клиентом конкретного кадра данных, и out является результатом объединения строк гроздь клиента - конкретные кадры данных.

Вы также можете ознакомиться с lubridate, что упростит работу с датами и временем. Как упоминалось в комментариях, также полезно было бы dplyr, равно как и остальная часть «Hadleyverse» пакетов для очистки и печати данных. Решения по вашим вопросам 1 и 2, а также весь процесс очистки и подведения итогов, будут намного чище и проще с помощью правильных инструментов.

+0

Спасибо. Очень полезно. Единственное, что мне нужно выяснить из этого, - это разделить его на разные данные по клиенту Доходом MTD: 2015. Тогда хорошо идти. Я попрошу об этом в другом посте, если это будет предпочтительнее. @landau –

+0

Обязательно. Если вы измените 'ddply' на' dlply' выше, у вас будет список кадров данных, специфичных для клиента, в 'out' вместо одного кадра данных. Семантически, я не уверен, что вы имеете в виду, когда говорите о разделении по доходам MTD: 2015. Обычно я думаю о разделении кадров данных в соответствии с такими функциями, как дата, а не такие уровни, как декабрь 2015 года. – landau

+0

Итак, когда я делаю это список, он заказывается в алфавитном порядке Клиентом. Я хочу заказать список клиентов по Доходу MTD 12: 2015 –

Смежные вопросы