Tcl 使用grep获取行号
我想使用Tcl 使用grep获取行号,tcl,Tcl,我想使用grep命令获取行号,但当搜索模式不是单个单词时,我会收到错误消息: couldn't read file "Pattern": no such file or directory 如何正确使用grep?代码如下: set status [catch {eval exec grep -n '$textToGrep' $fileName} lineNumber] if { $status != 0 } { #error } else { puts "lineNumber
grep
命令获取行号,但当搜索模式不是单个单词时,我会收到错误消息:
couldn't read file "Pattern": no such file or directory
如何正确使用grep?代码如下:
set status [catch {eval exec grep -n '$textToGrep' $fileName} lineNumber]
if { $status != 0 } {
#error
} else {
puts "lineNumber = $lineNumber"
}
此外,如果搜索模式根本不匹配,则返回值为:“子进程异常退出”
下面是一个简单的测试用例:
set textToGrep "<BBB name=\"BBBRM\""
set textToGrep”好吧,我还发现你的代码和一个单词模式有问题
首先,我认为您不需要eval
命令,因为catch
本身对其第一个参数进行求值
然后,问题是将$textToGrep
变量放在exec
中的单引号'
中,这对Tcl没有任何意义
因此,如果textToGrep
的内容是foo
,则要求grep
搜索字符串'foo'
。如果文件中未找到该字符串,包括单引号,则会出现错误
试着用英语重写你的第一行
set status [catch {exec grep -n $textToGrep $fileName} lineNumber]
看看它是否有效。另外,请阅读exec
手册页,它很好地解释了这些问题。好吧,我还发现您的代码和单个单词模式存在问题
set textToGrep {\<BBB name="BBBRM"}
catch {exec grep -n $textToGrep $fileName} status
if {![regexp "child process" $status]} {
puts $status
} else {
puts "no word found"
}
首先,我认为您不需要eval
命令,因为catch
本身对其第一个参数进行求值
然后,问题是将$textToGrep
变量放在exec
中的单引号'
中,这对Tcl没有任何意义
因此,如果textToGrep
的内容是foo
,则要求grep
搜索字符串'foo'
。如果文件中未找到该字符串,包括单引号,则会出现错误
试着用英语重写你的第一行
set status [catch {exec grep -n $textToGrep $fileName} lineNumber]
另外,请阅读exec
手册页,其中很好地解释了这些问题。set textToGrep{\set textToGrep{\这里有两个问题:
set textToGrep {\<BBB name="BBBRM"}
catch {exec grep -n $textToGrep $fileName} status
if {![regexp "child process" $status]} {
puts $status
} else {
puts "no word found"
}
- 模式匹配不起作用
- grep退出,子进程出现错误
未找到模式时异常退出
第一个问题是,您没有将textToGrep
括在双引号中(而不是单引号)。因此,您的代码应该是:
[catch {exec grep -n "$textToGrep" $fileName} lineNumber]
第二个问题是由于grep
命令的退出状态。grep
在找不到模式时出错退出。以下是试用shell:
# cat file
pattern
pattern with multiple spaces
# grep pattern file
pattern
pattern with multiple spaces
# echo $?
0
# grep nopattern file
# echo $?
1
编辑:
在您的情况下,您有一些特殊字符,例如
(在shell上有特殊含义)
set textToGrep“”textToGrep
这里有两个问题:
- 模式匹配不起作用
- grep退出,子进程出现错误
未找到模式时异常退出
第一个问题是,您没有将textToGrep
括在双引号中(而不是单引号)。因此,您的代码应该是:
[catch {exec grep -n "$textToGrep" $fileName} lineNumber]
第二个问题是由于grep
命令的退出状态。grep
在找不到模式时出错退出。以下是试用shell:
# cat file
pattern
pattern with multiple spaces
# grep pattern file
pattern
pattern with multiple spaces
# echo $?
0
# grep nopattern file
# echo $?
1
编辑:
在您的情况下,您有一些特殊字符,例如
(在shell上有特殊含义)
set textToGrep“”textToGrep
如果您的系统安装了tcllib,您可以使用fileutil
软件包中的fileutil::grep
命令:
package require fileutil
set fileName data.xml
set textToGrep {<BBB +name="BBBRM"}; # Update: Add + for multi-space match
set grepResult [::fileutil::grep $textToGrep $fileName]
foreach result $grepResult {
# Example result:
# data.xml:4: <BBB name="BBBRM" />
set lineNumber [lindex [split $result ":"] 1]
puts $lineNumber
# Update: Get the line, squeeze the spaces before name=
set line [lindex [split $result ":"] 2]
regsub { +name=} $line " name=" line
puts $line
}
包需要fileutil
设置文件名data.xml
设置textToGrep{如果系统安装了tcllib,则可以使用fileutil
软件包中的fileutil::grep
命令:
package require fileutil
set fileName data.xml
set textToGrep {<BBB +name="BBBRM"}; # Update: Add + for multi-space match
set grepResult [::fileutil::grep $textToGrep $fileName]
foreach result $grepResult {
# Example result:
# data.xml:4: <BBB name="BBBRM" />
set lineNumber [lindex [split $result ":"] 1]
puts $lineNumber
# Update: Get the line, squeeze the spaces before name=
set line [lindex [split $result ":"] 2]
regsub { +name=} $line " name=" line
puts $line
}
包需要fileutil
设置文件名data.xml
设置textToGrep{您确定文件包含您正在搜索的内容吗?查看exec
手册页,您有一个示例,可以使用try…except
或catch
进行检查。当文件中找不到模式时,grep
将以非零结果退出,并且您的脚本将显示错误。当然,是我正在搜索文件中的。我得到的错误如下:无法读取文件”模式应该是搜索":没有这样的文件或目录这是我的建议;无论问题是什么,它都回答了问题本身。你确定该文件包含你正在搜索的内容吗?查看exec
手册页,你有一个示例,当在文件,grep
以非零结果退出,您的脚本显示错误。当然,我正在搜索的模式在文件中。我得到的错误如下:无法读取文件“应该搜索的模式”:没有这样的文件或目录这是我的建议;不管问题是什么,它都回答了问题本身。你能给出变量textToGrep
,fileName
?以及文件的内容吗?你能给出变量textToGrep
,fileName
?以及file也是?谢谢你的回答。但我仍然得到相同的错误:无法读取文件“这是因为
在外壳上具有特殊意义。我已经用解决方案编辑了我的答案。谢谢你的回答。但我仍然得到相同的错误:无法读取文件”这是因为
在外壳上具有特殊的意义。我用解决方案编辑了我的答案。有没有一些方法可以从xml中删除grep之前的空格(尽管这与此问题无关)?你的意思是把空白删掉``使之成为
?我的意思是在属性之前删掉空白:所以我同意Hai Vu。我认为这是