Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Regex R两个逗号分隔字符串之间的匹配_Regex_R_Pattern Matching_Match - Fatal编程技术网

Regex R两个逗号分隔字符串之间的匹配

Regex R两个逗号分隔字符串之间的匹配,regex,r,pattern-matching,match,Regex,R,Pattern Matching,Match,我试图找到一种优雅的方法来查找数据帧中以下两个字符列之间的匹配。复杂的部分是,任何一个字符串都可以包含一个逗号分隔的列表,如果一个列表的一个成员与另一个列表的任何成员匹配,那么整个条目都将被视为匹配项。我不确定我解释得有多好,所以这里是示例数据和输出: 备选案文1: 在 A G CGTCC,AT CGC 备选案文2: AA A GG 在,GGT CG 每行的预期匹配: 第1行=无 第2行=A 第3行=无 第4行=AT 第5行=无 非工作解决方案: 第一次尝试:按所需列合并整个数据帧,

我试图找到一种优雅的方法来查找数据帧中以下两个字符列之间的匹配。复杂的部分是,任何一个字符串都可以包含一个逗号分隔的列表,如果一个列表的一个成员与另一个列表的任何成员匹配,那么整个条目都将被视为匹配项。我不确定我解释得有多好,所以这里是示例数据和输出:

备选案文1:

  • A
  • G
  • CGTCC,AT
  • CGC
备选案文2:

  • AA
  • A
  • GG
  • 在,GGT
  • CG
每行的预期匹配:

  • 第1行=无
  • 第2行=A
  • 第3行=无
  • 第4行=AT
  • 第5行=无
非工作解决方案:

第一次尝试:按所需列合并整个数据帧,然后匹配上面显示的alt列:

match1 = data.frame(merge(vcf.df, ref.df, by=c("chr", "start", "end",  "ref")))
matches = unique(match1[unlist(sapply(match1$Alt1 grep, match1$Alt2, fixed=TRUE)),])
第二种方法,使用VariantAnoatation/Granges中的FindVerlaps特征:

findoverlaps(ranges(vcf1), ranges(vcf2)) 
如有任何建议,将不胜感激!谢谢大家!

解决方案 感谢@Marat Talipov在下面的回答,以下解决方案可用于比较两个逗号分隔的字符串:

> ##read in edited kaviar vcf and human ref
> ref <-     readVcfAsVRanges("ref.vcf.gz", humie_ref)
Warning message:
In .vcf_usertag(map, tag, ...) :
  ScanVcfParam ‘geno’ fields not present: ‘AD’

> ##rename chromosomes to match with vcf files
> ref <- renameSeqlevels(ref, c("1"="chr1"))

> ##################################
> ## Gather VCF files to process  ## 
> ##################################
> ##data frame *.vcf.gz files in directory path
> vcf_path <- data.frame(path=list.files(vcf_dir, pattern="*.vcf.gz$",  full=TRUE))

> ##read in everything but sample data for speediness
> vcf_param = ScanVcfParam(samples=NA)
> vcf <- readVcfAsVRanges("test.vcf.gz", humie_ref, param=vcf_param)

> #################
> ## Match SNP's ##
> #################
> ##create data frames of info to match on
> vcf.df = data.frame(chr =as.character(seqnames(vcf)), start = start(vcf),     end = end(vcf), ref = as.character(ref(vcf)), 
+                     alt=alt(vcf), stringsAsFactors=FALSE)
> ref.df = data.frame(chr =as.character(seqnames(ref)), start =     start(ref), end = end(ref), 
+                     ref = as.character(ref(ref)), alt=alt(ref),     stringsAsFactors=FALSE)
> 
> ##merge based on all positional fields except vcf
> col_match = data.frame(merge(vcf.df, ref.df, by=c("chr", "start", "end", "ref")))

> library(stringi)
> ##split each alt column by comma and bind together
> M1 <- stri_list2matrix(sapply(col_match$alt.x,strsplit,','))
> M2 <- stri_list2matrix(sapply(col_match$alt.y,strsplit,','))
> M <- rbind(M1,M2)

> ##compare results
> result <- apply(M,2,function(z) unique(na.omit(z[duplicated(z)])))

> ##add results column to col_match df for checking/subsetting
> col_match$match = result
> head(col_match)
   chr    start      end ref alt.x alt.y match
1 chr1 39998059 39998059   A     G     G     G
2 chr1 39998059 39998059   A     G     G     G
3 chr1 39998084 39998084   C     A     A     A
4 chr1 39998084 39998084   C     A     A     A
5 chr1 39998085 39998085   G     A     A     A
6 chr1 39998085 39998085   G     A     A     A
##阅读编辑的kaviar vcf和人类参考
>ref##重命名染色体以与vcf文件匹配
>参考号##################################
>##收集VCF文件以进行处理##
> ##################################
>##数据框*.vcf.gz目录路径中的文件
>vcf#U路径##读取除样本数据外的所有数据以提高速度
>vcf_参数=扫描vcf参数(样本=NA)
>vcf#################
>##匹配SNP的##
> #################
>##创建要匹配的信息数据帧
>vcf.df=data.frame(chr=as.character(seqnames(vcf)),start=start(vcf),end=end(vcf),ref=as.character(ref(vcf)),
+alt=alt(vcf),stringsAsFactors=FALSE)
>ref.df=data.frame(chr=as.character(seqnames(ref)),start=start(ref),end=end(ref),
+ref=as.character(ref(ref)),alt=alt(ref),stringsAsFactors=FALSE)
> 
>##基于除vcf以外的所有位置字段合并
>col_match=data.frame(合并(vcf.df,ref.df,by=c(“chr”,“start”,“end”,“ref”))
>图书馆(stringi)
>##用逗号拆分每个alt列并绑定在一起
>M1 M2 M##比较结果
>结果##将结果列添加到列匹配df以进行检查/子集设置
>col_match$match=结果
>头部(col_匹配)
chr开始结束参考alt.x alt.y匹配
1 chr1 39998059 39998059 A G G
2 chr1 39998059 39998059 A G G
3 chr1 39998084 39998084 C A A
4 chr1 39998084 39998084 C A A
5 chr1 39998085 39998085 G A A
6 chr1 39998085 39998085 G A A

如果输入列表长度相等,并且希望以成对方式比较列表元素,则可以使用以下解决方案:

library(stringi)

M1 <- stri_list2matrix(sapply(Alt1,strsplit,','))
M2 <- stri_list2matrix(sapply(Alt2,strsplit,','))
M <- rbind(M1,M2)

result <- apply(M,2,function(z) unique(na.omit(z[duplicated(z)])))

你可以这样做:

Alt1 <- list('AT','A','G',c('CGTCC','AT'),'CGC')
Alt2 <- list('AA','A','GG',c('AT','GGT'),'CG')
# make sure you change the lists within in the lists into vectors

matchlist <- list()
for (i in 1:length(Alt1)){
  matchlist[[i]] <- ifelse(Alt1[[i]] %in% Alt2[[i]], 
                           paste("Row",i,"=",c(Alt1[[i]],Alt2[[i]])[duplicated(c(Alt1[[i]],Alt2[[i]]))],sep=" "),
                           paste("Row",i,"= none",sep=" ")) 
}
print(matchlist)

Alt1坚持使用
stringi
包,您可以使用来自Marat答案的
Alt1
Alt2
数据执行类似操作

library(stringi)

f <- function(x, y) {
    ssf <- stri_split_fixed(c(x, y), ",", simplify = TRUE)
    if(any(sd <- stri_duplicated(ssf))) ssf[sd] else NA_character_
}

Map(f, Alt1, Alt2)
# [[1]]
# [1] NA
# 
# [[2]]
# [1] "A"
# 
# [[3]]
# [1] NA
# 
# [[4]]
# [1] "AT"
# 
# [[5]]
# [1] NA
# 
# [[6]]
# [1] "GG" "CC"

Alt1和Alt2的长度相等吗?既然您使用的是“stringi”,为什么不使用
stri_split
,直接简化为一个矩阵?那么
mapply(match,Alt1,Alt2)
呢?@AnandaMahto,因为
stri_list2matrix
是我在
stringi
)度量中知道的唯一函数,它将只返回完全匹配的结果。问题还在于匹配逗号分隔子字符串。另外,我的输入列表长度不同。有没有办法修改它以适应不同的长度?这是一个很好的方法。。。谢谢。我想你可以用
交叉(Alt1[[I]],Alt2[[I]])替换
(Alt2[[I]]]%替换%Alt1[[I]])
(Alt1[[I]],Alt2[[I]])
我想你是对的!谢谢我现在不在r附近,我将稍后再试。我尝试了上述两种建议,收到了以下错误:
ifelse中的错误((Alt1[[I]]%在%Alt2[[I]]中)|(Alt2[[I]]%在%Alt1[[I]]中);:在为函数“ifelse”选择方法时评估参数“yes”时出错:在c中出错(Alt1[[I]],Alt2[[I]])[[any(重复的)(c(Alt1[[I]],Alt2[[i]])]]:尝试选择少于一个元素>打印(匹配列表)列表()
您确定alt1和Alt2是列表,如果是,它们的长度是否相同?太棒了,我来试一试!
Alt1 <- list('AT','A','G',c('CGTCC','AT'),'CGC')
Alt2 <- list('AA','A','GG',c('AT','GGT'),'CG')
# make sure you change the lists within in the lists into vectors

matchlist <- list()
for (i in 1:length(Alt1)){
  matchlist[[i]] <- ifelse(Alt1[[i]] %in% Alt2[[i]], 
                           paste("Row",i,"=",c(Alt1[[i]],Alt2[[i]])[duplicated(c(Alt1[[i]],Alt2[[i]]))],sep=" "),
                           paste("Row",i,"= none",sep=" ")) 
}
print(matchlist)
library(stringi)

f <- function(x, y) {
    ssf <- stri_split_fixed(c(x, y), ",", simplify = TRUE)
    if(any(sd <- stri_duplicated(ssf))) ssf[sd] else NA_character_
}

Map(f, Alt1, Alt2)
# [[1]]
# [1] NA
# 
# [[2]]
# [1] "A"
# 
# [[3]]
# [1] NA
# 
# [[4]]
# [1] "AT"
# 
# [[5]]
# [1] NA
# 
# [[6]]
# [1] "GG" "CC"
g <- function(x, y, sep = ",") {
    s <- scan(text = c(x, y), what = "", sep = sep, quiet = TRUE)
    s[duplicated(s)]
}
Map(g, Alt1, Alt2)