作者celestialgod (天)
看板R_Language
标题Re: [问题] 资料长<->宽变换
时间Sat Aug 13 13:08:02 2016
※ 引述《DrRd (就这样吧)》之铭言:
: [问题类型]:
:
: 意见调查(我对R 有个很棒的想法,想问问大家的意见)
:
: [软体熟悉度]:
:
: 入门(写过其他程式,只是对语法不熟悉)
: [问题叙述]:
:
: 要将宽型的资料转成长型的资料,但是要合并成的新变项有两个
: 以iris为例
: 本来iris的资料长这样
: | Sepal.Length | Sepal.Width | Petal.Length | Petal.Width | Species |
: |:------------:|:-----------:|:------------:|:-----------:|:-------:|
: | 5.1 | 3.5 | 1.4 | 0.2 | setosa |
: | 4.9 | 3.0 | 1.4 | 0.2 | setosa |
: | 4.7 | 3.2 | 1.3 | 0.2 | setosa |
: | 4.6 | 3.1 | 1.5 | 0.2 | setosa |
: 我想要转成
: | Species | SorP.x | Length | Width |
: |:-------:|:------------:|:------:|:-----:|
: | setosa | Sepal | 5.1 | 3.5 |
: | setosa | Sepal | 5.1 | 3.0 |
: | setosa | Pepal | 5.1 | 3.2 |
: | setosa | Pepal | 5.1 | 3.1 |
: | setosa | Sepal | 5.1 | 3.6 |
: 目前我想到的作法是先弄出两个长期的资料,一个是Length另一个是Width
: 然後再把两个merge起来,请问大家有没有什麽其他的方法?可以不用先弄成两个资料?
:
: [程式范例]:
:
: data("iris")
: head(iris)
: library(tidyr);library(dplyr)
: aa <- merge(
: gather(iris[-c(2,4)],key = SorP, value = Length, Sepal.Length, Petal.Length),
: gather(iris[-c(1,3)],key = SorP, value = Width, Sepal.Width, Petal.Width),
: by.x = "Species", by.y = "Species")
:
: [环境叙述]:
:
: R version 3.3.0 (2016-05-03)
: Platform: x86_64-apple-darwin13.4.0 (64-bit)
: Running under: OS X 10.11.6 (El Capitan)
:
: [关键字]:
:
: 资料格式、tidyr
好读版:
http://pastebin.com/Lei4AzsU
两个方法都可以达成,重点是unique key - id的建立
1. data.table
library(data.table)
library(pipeR)
resDT <- iris %>>% data.table %>>%
transform(Species = as.character(Species), id = 1:nrow(.)) %>>%
melt(id = 5:6, measure = c(1:4), variable.factor = FALSE) %>>%
`[`( , `:=`(c("partName", "measure"), tstrsplit(variable, "\\."))) %>>%
dcast.data.table(Species + partName + id~ measure, sum,
value.var = "value") %>>% `[`( , id := NULL)
# Species partName Length Width
# 1: setosa Petal 1.4 0.2
# 2: setosa Petal 1.4 0.2
# 3: setosa Petal 1.3 0.2
# 4: setosa Petal 1.5 0.2
# 5: setosa Petal 1.4 0.2
# ---
# 296: virginica Sepal 6.7 3.0
# 297: virginica Sepal 6.3 2.5
# 298: virginica Sepal 6.5 3.0
# 299: virginica Sepal 6.2 3.4
# 300: virginica Sepal 5.9 3.0
2. dplyr + tidyr
library(pipeR)
library(dplyr)
library(tidyr)
resTbl <- iris %>>% tbl_df %>>% mutate(id = 1:nrow(.)) %>>%
gather(variable, value, -Species, -id) %>>%
separate(variable, c("partName", "measure")) %>>%
spread(measure, value) %>>% select(-id)
# Source: local data frame [300 x 4]
#
# Species partName Length Width
# <fctr> <chr> <dbl> <dbl>
# 1 setosa Petal 1.4 0.2
# 2 setosa Sepal 5.1 3.5
# 3 setosa Petal 1.4 0.2
# 4 setosa Sepal 4.9 3.0
# 5 setosa Petal 1.3 0.2
# 6 setosa Sepal 4.7 3.2
# 7 setosa Petal 1.5 0.2
# 8 setosa Sepal 4.6 3.1
# 9 setosa Petal 1.4 0.2
# 10 setosa Sepal 5.0 3.6
# .. ... ... ... ...
--
R资料整理套件系列文:
magrittr #1LhSWhpH (R_Language) http://tinyurl.com/j3ql84c
data.table #1LhW7Tvj (R_Language) http://tinyurl.com/hr77hrn
dplyr(上) #1LhpJCfB (R_Language) http://tinyurl.com/jtg4hau
dplyr(下) #1Lhw8b-s (R_Language)
tidyr #1Liqls1R (R_Language) http://tinyurl.com/jq3o2g3
--
※ 发信站: 批踢踢实业坊(ptt.cc), 来自: 36.233.82.44
※ 文章网址: https://webptt.com/cn.aspx?n=bbs/R_Language/M.1471064884.A.2D4.html
※ 编辑: celestialgod (36.233.82.44), 08/13/2016 13:18:14
1F:→ DrRd: 十分详细,我再研究一下spread。感谢版主 08/13 21:52