7

I'd like to parse a file containing 5 digit numbers separated by comma or dash, lines like :
12345,23456,34567-45678,12345-23456,34567

My goal is to find lines which have incorrect formatting eg. lines which contain numbers which are not composed of 5 digits being separated by other characters than comma or dash.

I tried to egrep the file with :

cat file.txt | egrep -v [-,]*[0-9]{5}[,-]*

  • but if I have a 6 digit number, it is matched, and the line is not displayed
  • and if I have a 4 digit number, it is not matched but other numbers from that same line are matched and the line is not displayed

To specify the lines content :

  • a number must be of 5 digits
  • ranges are defined with dash, like 12345-12389
  • a line can contain anything from a single number to several numbers and ranges in any order

Any suggestions please ?

2
  • 2
    You might want to show some correct lines, and incorrect lines to give people more to go on (show as much variation as possible). Commented Apr 15, 2016 at 8:35
  • added some more details. maybe grep+regex is not the best solution to parse his....
    – magor
    Commented Apr 15, 2016 at 8:40

3 Answers 3

11
grep -vxE '([0-9]{5}[,-])*[0-9]{5}'

Would report the incorrect lines.

Or if you also want to forbid 12345-12345-12345:

num='[0-9]{5}'
num_or_range="$num(-$num)?"
grep -vxE "($num_or_range,)*$num_or_range"
5

For a good grep solution, see Stéphane's answer. As an alternative, here's a Perl one:

perl -ne 'print if grep{$_!~/^\d{5}$/} split(/[,-]/); ' file 

That will split each input line on , or - and then will look for members of the split array that don't consist of exactly 5 numbers. If any are found, the line is printed.

0
4

You don't need cat. Does this do what you want:

 $ grep -v -E '^([0-9]{5}(,|-))+' <FILE>

For example, if FILE had the following contents:

12345,23456,34567-45678,12345-23456,34567
1,2
12345*23456,34567-45678,12345-23456,34567
123456
1234*23456,34567-45678,12345-23456,34567

result would be:

$ grep -v -E '^([0-9]{5}(,|-))+' 5d
1,2
12345*23456,34567-45678,12345-23456,34567
123456
1234-23456,34567-45678,12345-23456,34567
3
  • 1
    This will fail if a line contains only 5 numbers.
    – terdon
    Commented Apr 15, 2016 at 8:38
  • Thanks for your effort ! As @terdon mentioned this fails in some cases, but it's very close.
    – magor
    Commented Apr 15, 2016 at 8:49
  • 2
    @mazs: ok, I thought you always expected - or , to be there between numbers. Commented Apr 15, 2016 at 8:50

You must log in to answer this question.

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