1

我有一个 csv 文件,其中包含以下格式的数据:

PrjID , 目标
1001 , (i) 提高效率 (ii) 降低成本 (iii) 最大化收入
1002 , a) 玩得开心 b) 学习新事物
1003 , (1) 变得棘手 (2) 挑战任务

第一个变量是 Id,第二个变量是文本变量“objective”。每个项目在单列中都有多个目标的数据,由 (i)、(ii)、..etc 或 (a)、(b)、(c)、..etc 或 (1)、(2) 分隔, (3),..等。现在我想要为项目的每个目标创建一个观察结果。很像这样:

PrjID , 目标
1001 , (i) 提高效率
1001 , (ii) 降低成本
1001 , (iii) 最大化收入
1002 , a) 玩得开心
1002 , b) 学习新事物
1003 , (1) 变得棘手
1003 , (2)具有挑战性的任务

对于只有一个目标的项目,它只有一行。但是对于多个目标,它会拆分观察。

我对在 R 中处理文本数据很陌生,一些 R 专业人士可以帮助我开始解决这个问题吗?提前致谢!

4

2 回答 2

4

这里有一个想法。

  1. 使用巧妙的正则表达式在您的目标列中插入一个新的分隔符
  2. 使用此分隔符strsplit将句子拆分为向量
  3. 使用by, 按 ID 处理前面的步骤。

按照这个步骤,我得到这个代码:

ll <- by(dat,dat$PrjID,FUN = function(x){
        x.delim <- gsub(" (\\(?[a-x,0-9]*\\))",'#\\1',x$Objective)
        obj  = unlist(strsplit(x.delim,'#'))
        data.frame(PrjID= x$PrjID,objective=obj[-1])
})
## transform your list to a data.frame
do.call(rbind,ll)

      PrjID                 objective
1001.1  1001 (i) To improve efficiency
1001.2  1001        (ii) Decrease cost
1001.3  1001   (iii) Maximize revenue 
1002.1  1002               a) Have fun
1002.2  1002      b) Learn new things 
1003.1  1003        (1) Getting tricky
1003.2  1003      (2) Challanging task

PS,这里的数据是:

dat <- read.table(text='PrjID, Objective 
1001 , (i) To improve efficiency (ii) Decrease cost (iii) Maximize revenue 
1002 , a) Have fun b) Learn new things 
1003 , (1) Getting tricky (2) Challanging task',sep=',',header=TRUE)
于 2013-05-21T12:33:05.087 回答
3

从 agstudy 的答案中摘取叶子,这是一个不使用魔术分隔符但不保留文本中点索引的解决方案:

// Matches:
// 1. Single letter prefixes: a), b) ... z)
// 2. Roman numerals (only small case): [i,x,c,m,v]+
// 3. Numeral indexes: [0-9]*
delim <- "((^|\\s)\\(?([a-z]|[i,x,c,m,v]+|[0-9]+)\\))"

ll <- by(dat, dat$PrjID, function (r) {
            each.obj <- str_split(r$Objective, delim)[[1]][-1]
            data.frame(PrjId = r$PrjID, Objective = str_trim(each.obj))
        })

do.call(rbind, ll)

       PrjId                     Objective
1001.1  1001     First(could be something)
1001.2  1001 Seconds (blah something else)
1001.3  1001      (how can thins be) Third
1002.1  1002         To improve efficiency
1002.2  1002                 Decrease cost
1002.3  1002              Maximize revenue
1003.1  1003                Getting tricky
1003.2  1003              Challanging task

dat在这种情况下是:

> dat
  PrjID
1  1001
2  1002
3  1003
                                                                                    Objective
1 (i) First(could be something) b) Seconds (blah something else) (3) (how can thins be) Third
2                        (i) To improve efficiency (ii) Decrease cost (iii) Maximize revenue
3                                                     (1) Getting tricky (2) Challanging task 
于 2013-05-21T15:03:56.223 回答