Tcl:使用sed命令时出错

时间:2015-12-24 07:45:16

标签: regex sed tcl

我的字符串如下:

  

str1.str2.strn-1。{I} .strn

我使用sed命令删除最后一个点后面的字符串'。'

proc check_str {str} {

set cmd "echo $str | sed -E 's/[^.]+$//'"

set new_str [exec sh -c $cmd]
puts "the new string is :$new_str"
}

但我收到了错误:

  

命令名称无效^。

并且不显示新字符串!

如何显示新字符串?

4 个答案:

答案 0 :(得分:2)

regsub命令匹配正则表达式并将替换应用于匹配的文本。这与你使用sed的s非常相似。

set new_str [regsub {[^.]+$} $str ""]

请注意,将正则表达式放在大括号中(在Tcl中非常类似于unix shell中的单引号)几乎总是很重要,因为它们通常包含Tcl元字符。在这种情况下,正则表达式包含[]$(尽管处于终端位置);它需要引用或者Tcl将尝试执行奇怪命名的命令^.它也可能被引用了反斜杠,但这很烦人且不清楚。

这也是你之前尝试提问的错误。使用exec sed是完全矫枉过正的。使用exec echo … | sed会更糟糕,就像在sh -c内部一样。正确的工具即将到来,并且效率更高(假设您已经在Tcl中)。

答案 1 :(得分:1)

我找到了一个使用tcl的解决方案:

regsub -- {[^.]+$} $str {} string

答案 2 :(得分:1)

另一种Tcl技术是将该字符串拆分为单词列表,使用点作为分隔符。用空字符串替换最后一个单词。加入这些话。

set str {str1.str2.strn-1.{i}.strn}
set words [split $str .]
lset words end ""
set new [join $words .]   # => str1.str2.strn-1.{i}.

另一种技术是找到字符串中最后一个点的索引。然后将子串从零到该索引

set new [string range $str 0 [string last . $str]]

IMO甚至regsub对此任务都是过度的。

答案 3 :(得分:1)

有一个命令几乎完全符合你的要求,除了它也删除了最后一个点 - 但是通过在末尾添加一个新点很容易解决:

set new [file rootname $str].
# => str1.str2.strn-1.{i}.

文档:file