TCL中两个列表中元素的部分模式匹配

时间:2017-07-26 18:54:02

标签: pattern-matching tcl

所以,让我说我有以下两个列表:

ListA包含:

{{feed_sesmmu1_qmusharemem_se_smmu0_int}
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_datvld}
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[31]}
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[30]} 
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[29]}
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[28]}
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[27]}
{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[26]}}

ListB

{{se_smmu0_int}
{se_smmu0_soc_rd_datvld}
{se_smmu0_soc_rd_dat[29]}
{se_smmu0_soc_rd_dat[31]}
{se_smmu0_soc_rd_dat[30]}
{se_smmu0_soc_rd_dat[28]} 
{se_smmu0_soc_rd_dat[26]}
{se_smmu0_soc_rd_dat[27]}}

现在我需要{feed_sesmmu1_qmusharemem_se_smmu0_soc_rd_dat[27]}来匹配{se_smmu0_soc_rd_dat[27]}listA的其他元素应与listB中的对应元素相匹配。

2 个答案:

答案 0 :(得分:1)

你可以用

完成
lmap s $ListB {
    lsearch -inline $listA *[string map {[ \\[ ] \\]} $s]
}

我们的想法是获取列表ListB中的每个项目,并在列表listA中搜索该项目。需要注意的是:ListB中的某些项目中包含括号([ ]),这些字符对于lsearch默认使用的glob搜索是特殊的。所以我们将逃脱它们:string map {[ \\[ ] \\]} $s。此外,ListB中的项目将成为listA中的后缀,因此我们需要为“任何字符”添加一个星号*

如果您没有lmap但又不想在lmap (for Tcl 8.5)链接中使用替代广告:

set result {}
foreach s $ListB {
    lappend result [lsearch -inline $listA *[string map {[ \\[ ] \\]} $s]]
}
puts $result

文档: foreachlappendlmap (for Tcl 8.5)lmaplsearchputssetstring

Tcl字符串匹配的语法:

  • *匹配零个或多个字符的序列
  • ?匹配单个字符
  • [chars]匹配字符给出的集合中的单个字符(^ 否定;范围可以 az
  • \x匹配字符 x ,即使该字符是特殊字符(*?[]\之一)

答案 1 :(得分:0)

这是一个带有显式foreach循环的解决方案,以防lmap不可用。如果支持基于范围的匹配,它还可以避免全局样式的字符串匹配:

proc endsWidth {s suffix} {
    set index end-[expr {[string length $suffix]-1}]
    return [expr {[string range $s $index end] eq $suffix}]
}

foreach b $listB {
    foreach a $listA {
        if {[endsWidth $a $b]} {
            puts "$a $b"
        }
    }
}