2014-04-04 42 views
0

我以为我确实将宽数据转换为long,并且我一直在使用它一段时间,但是最近我发现出了点问题。显然,代码是错误的,我似乎无法修复它。将复杂的宽数据转换为长R

宽泛的数据是复杂的,因为它包含了有关何人开始他/她的第一份工作,第二份工作等的信息。我想把它变成面板数据。

因此原始数据df如下所示:

id name gender job1 sjob1 ejob1 job2 sjob2 ejob2 job3 sjob3 ejob3 
1 Jane F  100 1990 1992 103 1993 1995 104 1994 1997 
2 Tom M  200 1978 1980 400 1981 1985 NA NA NA 

作业号码是工作代码,表明某些工作,即管理,销售等

以上是充满了很短的版本我有数据。需要的输出是:

id name gender year job 
1 Jane F  1990 100 
1 Jane F  1991 100 
1 Jane F  1992 100 
1 Jane F  1993 103 
1 Jane F  1994 104 
1 Jane F  1995 104 
1 Jane F  1996 104 
1 Jane F  1997 104 
2 Tom M  1978 200 
2 Tom M  1979 200 
2 Tom M  1980 200 
2 Tom M  1981 400 
2 Tom M  1982 400 
2 Tom M  1983 400 
2 Tom M  1984 400 
2 Tom M  1985 400 

我对广泛版本总共有大约1600个观察值。 (1600人)。我试过以下,但没有奏效:

df_long <-reshape(df, 
      varying=c("job1", "job2", "job3"), 
      v.names="job", 
      timevar="year", 
      times=c("sjob1", "sjob2", "sjob3"), 
      direction = "long") 

这实际上成功地在sjob1,sjob2,sjob3(每个任务的起始年)的顺序保留职位代码,但没有保存岁以下sjob1只是记录sjob1代替:

id name gender year job 
1 Jane F  sjob1 100 
1 Jane F  sjob2 103 
1 Jane F  sjob3 104 
2 Tom M  sjob1 200 
2 Tom M  sjob2 400 
2 Tom M  sjob3 NA 

以上是我的原始数据的例子,所以我想发表我的原始数据,以及:https://www.dropbox.com/s/ygbkd91ataqkwz5/origin_wide.RData

+1

难道这是HTTP的副本://计算器。com/questions/9004399/reshape-panel-data-wide-format-to-long-format? – krlmlr

+1

你的代码的结果与你期望的结果有什么不同? – krlmlr

+0

@krlmlr我编辑了这个问题!它设法按顺序放置“工作”,但没有吐出代码中创建的“年”变量的年份。 – song0089

回答

0

你可以做到这一点与plyr包:

# reading the data 
df <- read.table(text = "id name gender job1 sjob1 ejob1 job2 sjob2 ejob2 job3 sjob3 ejob3 
1 Jane F  100 1990 1992 103 1993 1995 104 1994 1997 
2 Tom M  200 1978 1980 400 1981 1985 NA NA NA", header = TRUE, strip.white = TRUE) 

# needed package 
require(plyr) 

# transforming the data 
df2 <- rbind(
    ddply(df, .(id, name, gender), mutate, year = sjob1, job = job1), 
    ddply(df, .(id, name, gender), mutate, year = ejob1, job = job1), 
    ddply(df, .(id, name, gender), mutate, year = sjob2, job = job2), 
    ddply(df, .(id, name, gender), mutate, year = ejob2, job = job2), 
    ddply(df, .(id, name, gender), mutate, year = sjob3, job = job3), 
    ddply(df, .(id, name, gender), mutate, year = ejob3, job = job3) 
) 

# getting rid off NA's & ordering the dataframe by id 
df2 <- na.omit(df2[order(df2$id),c(1:3,13,14)]) 
+0

这很像魔术,非常感谢! – song0089

0

下面是使用reshape2草图和plyr

第1步:重塑一个“长”格式,这是你要找的内容有所不同:

library(reshape2) 
df.m <- melt(df, id.vars=c("id", "name", "gender")) 

这会给你开始和结束时间,以及分类,对就业机会。

第2步:隔离作业ID:

df.m$job.id <- as.integer(gsub("^(.*job)([0-9]+)$", "\\2", df.m$variable)) 
df.m$variable <- gsub("^(.*)([0-9]+)$", "\\1", df.m$variable) 

第3步:你可以计算工作分类的表中的每个人的ID和作业ID(连同姓名和性别):

library(plyr) 
df.jc <- rename(subset(df.m, variable=="job", select=c("id", "name", "gender", "value")), variable=job) 

步骤4:要获得完整的结果,您需要dcast数据以获得“宽”格式,其中包含两列sjobejob以及每个作业ID的每个人员ID一个观察值。然后,您可以adply生成一个年份序列,并将其合并回df.jc

我还没有测试代码,也不能给你最后一步的东西,因为我无法轻松读取示例数据。如果您的数据为dput,那会非常有帮助。请提出一个单独的,更详细的问题以解决进一步的问题,并提供一些代码和数据。

+0

谢谢,我应该发布整个原始宽版本的数据吗? – song0089

+0

对于第三步,我得到了重命名错误错误(子集(df.m,变量==“作业”,选择= c(“id”,“名称”,: 未使用的参数(变量=作业) – song0089

+0

@ Rusuer9000 :错误的语法,我的错误,你可以尝试'rename(...,list(variable =“job”))'? – krlmlr