2017-03-13 1 views
0

큰 데이터 세트가 있습니다.이 데이터 세트는 영역 열을 기반으로 여러 데이터 세트로 분할 한 다음 각 영역에 대한 코드 세트를 실행하고 각 영역에 대한 출력 데이터를 얻는 데 필요합니다. for 루프를 사용하여이 작업을 시도했지만 작동하지 않는 것 같습니다. 이것이 어떻게 달성 될 수 있는가. 미안 해요, 난 여전히 R을 학습 가능성에 대해 확실하지 오전 우리가 R.에서 같은 것을 할 수R 열에서 코드 목록 반복하기

for (a in c('10','11','14','20','30','40','50','61','64')) 
{ 
    paste0("data3_add_area",a) <- data3_add[AREACODE == a,] 
    paste0("in_add_area",a) <- in_add[AREA_CODE == a,] 

    source1 <- paste0("data3_add_area",a)$name 
    source2 <- paste0("in_add_area",a)$name 
    ..... 
    paste0("match_",a) <- output 

} 

- 아래 내가하려고했던 코드입니다. 이것을 달성하는 가장 좋은 방법은 무엇입니까?

편집 - 나는 각 영역 (이 링크에서 심판 - https://www.r-bloggers.com/fuzzy-string-matching-a-survival-skill-to-tackle-unstructured-information/) 복제 할 샘플 데이터

Address1 <- c("786, GALI NO 5, XYZ","rambo, 45, strret 4, atlast, pqr","23/4, 23RD FLOOR, STREET 2, ABC-E, PQR","45-B, GALI NO5, XYZ","HECTIC, 99 STREET, PQR") 
AREACODE <- c('10','11','14','20','30') 
Year1 <- c(2001:2005) 

Address2 <- c("abc, pqr, xyz","786, GALI NO 4 XYZ","45B, GALI NO 5, XYZ","del, 546, strret2, towards east, pqr","23/4, STREET 2, PQR","abc, pqr, xyz","786, GALI NO 4 XYZ","45B, GALI NO 5, XYZ","del, 546, strret2, towards east, pqr","23/4, STREET 2, PQR") 
Year2 <- c(2001:2010) 
AREA_CODE <- c('10','11','14','20','30','40','50','61','64') 

data3_add <- data.table(Address1,Year1,AREACODE) 
in_add <- data.table(Address2,Year2,AREA_CODE) 
in_add [,unique_id := sprintf("%06d", 1:nrow(in_add))] 

CODE 방법 2를 사용

나는 각각의 코드를 복제 할 지역 -

#install.packages('stringdist') 
library(stringdist) 

distance.methods<-c('osa','lv','dl','hamming','lcs','qgram','cosine','jaccard','jw') 
dist.methods<-list() 
for(m in 1:length(distance.methods)) 
{ 
    dist.name.enh<-matrix(NA, ncol = length(source2.devices$name),nrow = length(source1.devices$name)) 
    for(i in 1:length(source2.devices$name)) { 
    for(j in 1:length(source1.devices$name)) { 
     dist.name.enh[j,i]<-stringdist(tolower(source2.devices[i,]$name),tolower(source1.devices[j,]$name),method = distance.methods[m])  
     #adist.enhance(source2.devices[i,]$name,source1.devices[j,]$name) 
    } 
    } 
    dist.methods[[distance.methods[m]]]<-dist.name.enh 
} 

match.s1.s2.enh<-NULL 
for(m in 1:length(dist.methods)) 
{ 

    dist.matrix<-as.matrix(dist.methods[[distance.methods[m]]]) 
    min.name.enh<-apply(dist.matrix, 1, base::min) 
    for(i in 1:nrow(dist.matrix)) 
    { 
    s2.i<-match(min.name.enh[i],dist.matrix[i,]) 
    s1.i<-i 
    match.s1.s2.enh<-rbind(data.frame(s2.i=s2.i,s1.i=s1.i,s2name=source2.devices[s2.i,]$name, s1name=source1.devices[s1.i,]$name, adist=min.name.enh[i],method=distance.methods[m]),match.s1.s2.enh) 
    } 
} 
# Let's have a look at the results 
library(reshape2) 
matched.names.matrix<-dcast(match.s1.s2.enh,s2.i+s1.i+s2name+s1name~method, value.var = "adist") 
View(matched.names.matrix) 
+0

일부 재현 가능한 데이터를 제공 할 수 있습니까? 'dput (head (data2_add, 20))'과'in_add'를 사용합니다. – drmariod

+1

어쩌면 당신은'split'을 찾고 있는데, 이것은 어떤 벡터의 값에 기초하여 data.frame을 data.frames의리스트로 나눌 수 있습니다. 'myList <- split (data3_add, data3_add $ AREACODE)'입니다. gregor의 [this post] (http://stackoverflow.com/questions/17499013/how-do-i-make-a-list-of-data-frames)에 대한 답변은 data.frames 목록 작업에 도움이 될 수 있습니다. . – lmo

+1

@Frank, 지적 해 주셔서 감사합니다. 샘플 코드를 업데이트했습니다. – user1412

답변

0

다음은 완전한 스크립트입니다. 거리 행렬에 행과 열이 둘 이상인 상황을 보여주기 위해 입력 세트를 약간 변경했습니다.

library("stringdist") 
library("data.table") 

Address1 <- c("786, GALI NO 5, XYZ","rambo, 45, strret 4, atlast, pqr","23/4, 23RD FLOOR, STREET 2, ABC-E, PQR","45-B, GALI NO5, XYZ","HECTIC, 99 STREET, PQR") 
AREACODE <- c('10','10','14','20','30') 
Year1 <- c(2001:2005) 

Address2 <- c("abc, pqr, xyz","786, GALI NO 4 XYZ","45B, GALI NO 5, XYZ","del, 546, strret2, towards east, pqr","23/4, STREET 2, PQR","abc, pqr, xyz","786, GALI NO 4 XYZ","45B, GALI NO 5, XYZ","del, 546, strret2, towards east, pqr","23/4, STREET 2, PQR") 
Year2 <- c(2001:2010) 
AREA_CODE <- c('10','10','10','20','30','40','50','61','64', '99') 

data1 <- data.table(Address1, Year1, AREACODE) 
data2 <- data.table(Address2, Year2, AREA_CODE) 
data2[, unique_id := sprintf("%06d", 1:nrow(data2))] 

methods <- c('osa','lv','dl','hamming','lcs','qgram','cosine','jaccard','jw') 

# split data.table into list of data.tables by area code 
sdata1 <- split(data1, data1$AREACODE) 
sdata2 <- split(data2, data2$AREA_CODE) 

# find the unique codes 
codes <- union(names(sdata1), names(sdata2)) 


dist_calc <- function(x, y, methods) { 
    distance_methods <- list() 

    # calculate distance for each method 
    for(m in seq_along(methods)) { 
    output <- matrix(NA, ncol = length(x), nrow = length(y)) 
    for(i in seq_along(x)) { 
     for(j in seq_along(y)) { 
     # calculate the matrix of distances for each pairing 
     output[j, i] <- stringdist(tolower(x[i]), tolower(y[j]), method = methods[m]) 
     } 
    } 
    # store the output matrix in a named list element 
    distance_methods[[methods[m]]] <- output 
    } 
    # return a list of lists, with each leaf element being a matrix 
    return(distance_methods) 
} 


# iterate over codes, use names to retain codes and do not simplify -- return a list 
distances <- sapply(codes, function(code) { 
    x <- sdata1[[code]]$Address1 
    y <- sdata2[[code]]$Address2 

    # do not compute if the code is not present in either one, the other or both 
    if (is.null(x) | is.null(y)) 
    return(NULL) 

    # calculate all the distances 
    dist_mats <- dist_calc(x, y, methods) 

    # calculate the minimum value and indicie for each method 
    method_mins <- sapply(methods, function(meth) { 

    min_col <- apply(dist_mats[[meth]], 1, which.min) 
    min_val <- apply(dist_mats[[meth]], 1, min) 

    # list the minimum match value, the string, the matching string 
    data.table(name = y, match_name = x[min_col], adist = min_val) 
    }, USE.NAMES = TRUE, simplify = FALSE) 

    # combine into a single data.table 
    rbindlist(method_mins, idcol = "method") 

}, USE.NAMES = TRUE, simplify = FALSE) 

all_distances <- rbindlist(Filter(function(x) !is.null(x), distances), idcol = "AREACODE") 

# AREACODE method         name      match_name  adist 
# 1:  10  osa      abc, pqr, xyz    786, GALI NO 5, XYZ 12.00000000 
# 2:  10  osa     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 2.00000000 
# 3:  10  osa     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 3.00000000 
# 4:  10  lv      abc, pqr, xyz    786, GALI NO 5, XYZ 12.00000000 
# 5:  10  lv     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 2.00000000 
# 6:  10  lv     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 3.00000000 
# 7:  10  dl      abc, pqr, xyz    786, GALI NO 5, XYZ 12.00000000 
# 8:  10  dl     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 2.00000000 
# 9:  10  dl     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 3.00000000 
#10:  10 hamming      abc, pqr, xyz    786, GALI NO 5, XYZ   Inf 
#11:  10 hamming     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ   Inf 
#12:  10 hamming     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 3.00000000 
#13:  10  lcs      abc, pqr, xyz    786, GALI NO 5, XYZ 18.00000000 
#14:  10  lcs     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 3.00000000 
#15:  10  lcs     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 6.00000000 
#16:  10 qgram      abc, pqr, xyz    786, GALI NO 5, XYZ 16.00000000 
#17:  10 qgram     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 3.00000000 
#18:  10 qgram     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 6.00000000 
#19:  10 cosine      abc, pqr, xyz rambo, 45, strret 4, atlast, pqr 0.31400566 
#20:  10 cosine     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 0.04653741 
#21:  10 cosine     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 0.08784068 
#22:  10 jaccard      abc, pqr, xyz rambo, 45, strret 4, atlast, pqr 0.63157895 
#23:  10 jaccard     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 0.12500000 
#24:  10 jaccard     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 0.29411765 
#25:  10  jw      abc, pqr, xyz    786, GALI NO 5, XYZ 0.42535425 
#26:  10  jw     786, GALI NO 4 XYZ    786, GALI NO 5, XYZ 0.05360624 
#27:  10  jw     45B, GALI NO 5, XYZ    786, GALI NO 5, XYZ 0.10526316 
#28:  20  osa del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 29.00000000 
#29:  20  lv del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 29.00000000 
#30:  20  dl del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 29.00000000 
#31:  20 hamming del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ   Inf 
#32:  20  lcs del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 41.00000000 
#33:  20 qgram del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 35.00000000 
#34:  20 cosine del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 0.46394373 
#35:  20 jaccard del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 0.72000000 
#36:  20  jw del, 546, strret2, towards east, pqr    45-B, GALI NO5, XYZ 0.54863548 
#37:  30  osa     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 11.00000000 
#38:  30  lv     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 11.00000000 
#39:  30  dl     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 11.00000000 
#40:  30 hamming     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR   Inf 
#41:  30  lcs     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 15.00000000 
#42:  30 qgram     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 13.00000000 
#43:  30 cosine     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 0.21927994 
#44:  30 jaccard     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 0.50000000 
#45:  30  jw     23/4, STREET 2, PQR   HECTIC, 99 STREET, PQR 0.31607428 
# AREACODE method         name      match_name  adist 
+0

해결책 주셔서 감사합니다. 이것은 매우 흥미 롭습니다. 그러나 똑같은 방식으로 생각했던 것처럼 반복하기가 쉽지 않습니다. 해당 영역을 목록으로 유지해야합니까? 왜 우리가 두 가지 [[]]를 사용해야하는지 알려 주시면 도움이 될 것입니다. 각 영역에 대해 복제하려는 코드를 추가했습니다. 각 영역에 대한 출력을 얻기 위해 [[]]을 (를) 추가해야하는 곳을 제안하십시오. 죄송하지만 복제하려고했지만 원자 계산기에 대해 $ 연산자가 올바르지 않습니다. – user1412

+0

[this] (http://stackoverflow.com/questions/1169456/the-difference-between-and-notations-html/) 우리가'['를 사용할 때와'[['' – mlegge

+0

] 코드를 복제 해 주셔서 감사합니다. 나는 코드를 실행하려했지만 코드 마지막 줄에서 오류가 발생했습니다. "rbindlist (distance, idcol ="AREACODE ")의 오류 : SET_STRING_ELT에서 인덱스 5/5를 설정하려고 시도했습니다." 오류 및 봤어요 소식을 data.table을 업데이 트하고 내가이 업데이 트 여전히 같은 오류를 보았다. 이 오류의 원인을 알 수 있습니까? – user1412