2014-02-13 66 views
0

我有一個數據集,看起來像這樣:[R相當於itertools.chain

t x y 
1 0 0 0 
2 1 10 9 
3 2 20 18 
4 3 30 27 
... 

我想崩潰擴大數據集的每一行垂直放入一個新列z。我們的目標將是這個樣子:

t z 
1 0 0 
2 0 0 
3 1 10 
4 1 9 
5 2 20 
6 2 18 
7 3 30 
8 3 27 
... 

在Python中,我會用itertools.chain用於此目的:

import itertools 

# Make some fake data 
data = [{'t':t, 'x':t*10, 'y':t*9} for t in xrange(10)] 
# [ {'t': 0, 'y': 0, 'x': 0}, 
# {'t': 1, 'y': 9, 'x': 10}, 
# {'t': 2, 'y': 18, 'x': 20}, 
# ...] 

# transformation... 
list(itertools.chain(*(({'t':x['t'], 'z':x['x']}, {'t':x['t'], 'z':x['y']}) 
         for x in data) 
    )) 
# [{'z': 0, 't': 0}, 
# {'z': 0, 't': 0}, 
# {'z': 10, 't': 1}, 
# {'z': 9, 't': 1}, 
# {'z': 20, 't': 2}, 
# {'z': 18, 't': 2}, 
# ...] 

我犯了很多不同的嘗試與重塑包(meltt分組似乎如此接近我想要的,但排序t是不穩定的,據我所知)。

+0

也許你可以澄清爲什麼你使用'melt'的嘗試似乎只是'接近'你想要的,而你'按t排序並不穩定'的含義。謝謝! – Henrik

回答

1
library(reshape2) 
df2 <- melt(df, id.vars = "t") 
df2 
# t variable value 
# 1 0  x  0 
# 2 1  x 10 
# 3 2  x 20 
# 4 3  x 30 
# 5 0  y  0 
# 6 1  y  9 
# 7 2  y 18 
# 8 3  y 27 

可能對行進行排序,並選擇相關的列。

df2[order(df2$t), c("t", "value")] 
# t value 
# 1 0  0 
# 5 0  0 
# 2 1 10 
# 6 1  9 
# 3 2 20 
# 7 2 18 
# 4 3 30 
# 8 3 27 
+0

對於保證輸出的'x','y'排序,最後一條語句應該是'df2 [order(df2 $ t,df2 $ variable)),c(「t」,「value」)]'? –

+0

如果你看看'df2 [order(df2 $ t)'],那麼x-y順序很好,所以不需要。但是,爲什麼不明確他們的訂單! – Henrik

1

您可以用實現這一點,例如

dfx.temp <- df[,c(1,2)] 
dfy.temp <- df[,c(1,2)] 
names(dfx.temp) <- c("t","z") 
names(dfy.temp) <- c("t","z") 
df <- rbind(dfx.temp, dfy.temp) 

添加df <- df[order(df$t),]得到它在你問的確切順序。

+0

這看起來不錯,但我似乎無法找到任何文件說'訂單'是保證穩定的排序。 'y's不能在'x's前面結束。 –

1

下面是其他兩個選項...

melt,但在基礎R:

out <- cbind(t = mydf[, 1], stack(mydf[-1])) 
out[order(out$t, out$ind), c("t", "values")] 
# t values 
# 1 0  0 
# 5 0  0 
# 2 1  10 
# 6 1  9 
# 3 2  20 
# 7 2  18 
# 4 3  30 
# 8 3  27 

A 「data.table」 的方法:

library(data.table) 
DT <- data.table(mydf) 
DT[, unlist(.SD), by = "t"] 
# t V1 
# 1: 0 0 
# 2: 0 0 
# 3: 1 10 
# 4: 1 9 
# 5: 2 20 
# 6: 2 18 
# 7: 3 30 
# 8: 3 27 

兩個示例使用以下內容作爲「mydf」:

mydf <- data.frame(t = 0:3, x = seq(0, 30, 10), y = seq(0, 27, 9))