【问题标题】:replace space only between parentheses仅替换括号之间的空格
【发布时间】:2012-12-17 07:24:46
【问题描述】:

在一个字符串中,我试图用下划线替换括号之间的所有空格。例如,给定this ( is my ) simple example,我想得到this (_is_my_) simple example。

我正在研究 bash,并想为 sed 创建一个替换表达式,但是我想不出一个简单的单行解决方案。

期待您的帮助

【问题讨论】:

  • this ( is ( another ) simple ) example 和 this ( is ( my ) not so simple example 会发生什么?
  • 这两个问题都很好。对于我来说,嵌套括号并不重要,因为数据结构非常好。我尝试了很多不高级的 sed 东西,但要么什么都没有,要么所有的空间都被替换了。

标签: regex bash sed awk


【解决方案1】:

使用 sed:

sed ':l s/\(([^ )]*\)[ ]/\1_/;tl' input

如果括号不平衡:

sed ':l s/\(([^ )]*\)[ ]\([^)]*)\)/\1_\2/;tl' input

【讨论】:

  • 这个答案已经很老了。但是,我花了一些时间来完全理解这个正则表达式。因此,我简要说明一下::l 和;tl 中的l(小写L)是一个任意标签。也可以是a。正确的?真正好的想法是我们迭代这条线,如果我们成功地使用s/.../.../,我们会跳转到:[LABEL] [REGEX];t[LABEL] 的开头。因此,只要我们有成功的命中,我们就迭代一行?对吗?
【解决方案2】:
$ cat file
this ( is my ) simple example
$ awk 'match($0,/\([^)]+\)/) {str=substr($0,RSTART,RLENGTH); gsub(/ /,"_",str); $0=substr($0,1,RSTART-1) str substr($0,RSTART+RLENGTH)} 1' file
this (_is_my_) simple example

如果模式可以在一行上出现多次,则将 match() 放入循环中。

【讨论】:

    【解决方案3】:

    使用真正的编程语言:

    #!/usr/bin/python
    
    import sys
    
    for line in sys.stdin:
        inp = False
        for x in line:
            if x == '(':
                inp = True
            elif x == ')':
                inp = False
            if inp == True and x == ' ':
                sys.stdout.write('_')
            else:
                sys.stdout.write(x)
    

    这只处理最简单的情况,但应该很容易扩展到更复杂的情况。

    $echo "this ( is my ) simple case"|./replace.py
    $this (_is_my_) simple case
    $
    

    【讨论】:

    • sed 图灵完备,什么是真正的编程语言?
    【解决方案4】:

    假设没有嵌套括号或破括号对,最简单的方法是像这样使用Perl:

    perl -pe 's{(\([^\)]*\))}{($r=$1)=~s/ /_/g;$r}ge' file
    

    结果:

    this (_is_my_) simple example
    

    【讨论】:

      【解决方案5】:

      这可能对你有用(GNU sed):

      sed 's/^/\n/;ta;:a;s/\n$//;t;/\n /{x;/./{x;s/\n /_\n/;ta};x;s/\n / \n/;ta};/\n(/{x;s/^/x/;x;s/\n(/(\n/;ta};/\n)/{x;s/.//;x;s/\n)/)\n/;ta};s/\n\([^ ()]*\)/\1\n/;ta' file
      

      这适合多行嵌套的括号。但是它可能非常慢。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2021-03-05
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-10-31
        • 1970-01-01
        • 2015-05-08
        相关资源
        最近更新 更多