If I wanted to remove everything before a character (say "("), I would just do something like this 's/.*(//g'. Now I want to remove only certain things before a character/some characters, in my case - and before ( (including space)

I tried a few things but none worked. One example is:

sed 's/ *(/(/g'

But this only removed the space before and not the others, which makes sense to me when reading the code (it will remove everything between the space and (, but I had to try something before asking here), so I tried this: (which also didn't work)

sed 's/* (/(/g'

But this time I can't see why not. I thought it was because spaces are pretty special characters so I tried with - instead (s/*- (/(/g' and s/*-* (/(/g') but they didn't work either.


081 379 62 49 (Hems)
081-379-62-49 (Hems) 

Desired output:

0813796249 (Hems)
  • Please define "didn't work", including any error messages you may have been given. Dec 3, 2015 at 1:31
  • 1
    Show your input and your desired output. Dec 3, 2015 at 1:36
  • @roaima, if there were any error messages I would have said them. Sorry for just assuming, but I thought people would understand I meant that file/words didn't change as I like. Dec 3, 2015 at 2:03
  • @glennjackman inputs are either 081 379 62 49 (Hems) or 081-379-62-49 (Hems) and output is 0813796249 (Hems) Dec 3, 2015 at 2:09

2 Answers 2


You want to remove all spaces and dashes immediately before (? Then you need to use a character class or "bracket expression" including space and dash: [- ]

sed -e 's/[- ]*(/(/g'

See man 7 regex and search for bracket expression for more details.

With the input you mentioned (081 379 62 49 (Hems) or 081-379-62-49 (Hems)), you can do it with awk:

awk -F'(' 'BEGIN {OFS=" ("} ; {gsub(/[- ]/,"",$1) ; print}'

this tells awk to use ( as field separator, and then uses the gsub() function to remove spaces and dashes from the first field (the phone number). The Output Field Separator (OFS) is set to ( (space and () in order to produce the correct output.


echo -e "081 379 62 49 (Hems)\n081-379-62-49 (Hems)" | 
    awk -F'(' 'BEGIN {OFS=" ("} ; {gsub(/[- ]/,"",$1) ; print}'
0813796249 (Hems)
0813796249 (Hems)

BTW if there are no spaces or dashes after the phone number (e.g. inside the (...)) you could also do this with sed:

echo -e "081 379 62 49 (Hems)\n081-379-62-49 (Hems)" | 
    sed -e 's/[ -]//g ; s/(/ (/'

This strips ALL spaces and dashes from the input line, and then puts one space back immediately before the (. It will uglify the output horrendously if there are multiple words inside the parentheses (comment/name field?)

There's probably some baroquely complicated way of doing it properly in sed by copying the phone number to hold space and modifying it there and then re-inserting it back into the output line, but it's much easier to do it wth awk.

  • Not immediately before, but I also meant ` (` . A space before (. Dec 3, 2015 at 2:06
  • if you don't mean immediately before, then what do you mean? you need to be much clearer in expressing your goal.
    – cas
    Dec 3, 2015 at 2:09
  • This might be a language issue, because I don't speak English natively, but exactly what do you mean with "immediately before"? I thought you meant everything before ( but "everything" stops when there's a space. Dec 3, 2015 at 2:14
  • Thanks. I really need to learn awk, it seems to be more efficient than sed. Dec 3, 2015 at 2:19
  • sed is often a lot faster and simpler to use than awk but has its limitations....and that's where awk or perl should be used.
    – cas
    Dec 3, 2015 at 2:22

this works with sed:

printf %s\\n '081 379 62 49 (Hems)' \
             '081-379-62-49 (Hems)' |
sed 's/\( ([^)]*)\)\{0,1\}[ -]\{0,1\}/\1/g'

0813796249 (Hems)
0813796249 (Hems)

The trick is to let sed remove a null string when it isn't removing one of the strings you want it to. In that way the global substitution can span the entire pattern space removing a bunch of nothing - (\{0,1\} - 0 or 1 occurrences) - until it lights on some targeted character and substitutes it away, or replaces it with itself - as it will do for any characters occurring between a pair of ().

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .