简体   繁体   中英

Bash regex: replace string with any number of characters

I'm trying to remove colouring codes from a string; eg from: \\033[36;1mDISK\\033[0m to: DISK

my regex looks like this: \\033.*?m so match '\\033' followed by any number of chars, terminated by 'm'

when I search for the pattern, it finds a match; [[ "$var" =~ $regex ]] evaluates to true

however when I try to replace matches, nothing happens and the same string is returned.

Here's my complete script:

regex="\033.*?m"
var="\033[36;1mDISK\033[0m"

if [[ "$var" =~ $regex ]]
then
        echo "matches"
        echo ${var//$regex}
else
        echo "doesn't match!"
fi

The problem appears to be with the match any number of any character part of the regex. I can successfully replace DISK but if I change that to D.*K or D.*?K it fails.

Note in all above cases the pattern claims to match the string but fails when replacing. Not too sure where to go with this now, any help appreciated.

Thanks

The following should do it:

$ var="\033[36;1mDISK\033[0m"
$ newvar=$(printf ${var} | sed -r "s/\x1B\[([0-9]{1,2}(;[0-9]{1,2})?)?[m|K]//g")
$ echo ${newvar}

returns:

DISK

Now verify!

$ echo $var | od
0000000 030134 031463 031533 035466 066461 044504 045523 030134
0000020 031463 030133 005155
0000026
$ echo $newvar | od
0000000 044504 045523 000012
0000005

To use the parameter expansion substitution operator, you need to use an extended glob.

shopt -s extglob
newvar=${var//\\033\[*([0-9;])m}

To break it down:

  • \\\\033\\[ - match the encoded escape character and [ .
  • *([0-9;]) - match zero or more digits or semicolons. You could use +([0-9;]) to (more correctly?) match one or more digits or semicolons
  • m - the trailing m .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM