2

I have a line like

Xckt VDD VSS sig[1] sig[2] sig[3] sig[4] sig[5] sig[6] CKT

and I want to find the position of sig[4] in the line. In this case it should return 7. I wanted some simple script/ one liner in bash to do the same. In case of repeated match, if serial number of all occurrences of the match in the line would be great.

  • If any of the existing answers solves your problem, please consider accepting it via the checkmark. Thank you! – Jeff Schaller Apr 23 '17 at 13:04
3

You can do it with awk like this:

awk '{for(i=1;i<=NF;i++)if($i=="sig[4]")print i}'

That should work for you even in case of multiple entries.

If you need all the numbers on the same line, you can replace print with printf and adjust accordingly.

  • 1
    echo 'Xckt VDD VSS sig[1] sig[2] sig[3] sig[4] sig[5] sig[6] CKT' | grep -aob 'sig\[4]' Returns: 34:sig[4] I needed the position of the word rather than the 1st character for the match in the line. Th expected answer for me is 7 unline 34 coming from "grep -aob" – Pratap Apr 24 '16 at 21:40
  • yep, you are write. sorry I read the question a bit inattentively. the answer is updated. – rush Apr 24 '16 at 21:43
1

rush has a nice one-liner solution; here's a simple bash function that prints out all of the matches in the string:

function pratappos() {
  target=$1; shift
  pos=1
  while [[ $# -gt 0 ]]
  do
    [[ "$1" = "$target" ]] && echo $pos
    shift; ((++pos))
  done
  unset target pos
}

It's generalized to search for any string in a given list, so for example, you would set up that function (in your .bashrc, or into your current shell), then call it like:

pratappos sig[4] Xckt VDD VSS sig[1] sig[2] sig[3] sig[4] sig[5] sig[6] CKT
7

or (two matches):

pratappos sig[4] Xckt VDD VSS sig[1] sig[2] sig[3] sig[4] sig[5] sig[6] CKT sig[4]
7
11

... where the first parameter that you pass to it is taken as the string you want to search for, followed by the rest of the string to search in. It determines the position of the arguments using shift, which will see your given string as separated by $IFS.

To clarify the preceding point:

pratappos 'foo bar' a b foo bar 'foo bar' rest here
5
0

You could do it with perl, for example using the List::MoreUtils module as described in [perl] Get indexes of matches in array

perl -MList::MoreUtils=indexes -alne '
  print $_+1 for indexes { $_ eq "sig[4]" } @F
'

Testing with the given input line

$ perl -MList::MoreUtils=indexes -alne '
  print $_+1 for indexes { $_ eq "sig[4]" } @F
' <<< "Xckt VDD VSS sig[1] sig[2] sig[3] sig[4] sig[5] sig[6] CKT"
7

and with a line containing multiple instances

$ perl -MList::MoreUtils=indexes -alne '
  print $_+1 for indexes { $_ eq "sig[4]" } @F
' <<< "Xckt VDD VSS sig[1] sig[2] sig[3] sig[4] sig[5] sig[6] sig[4] CKT"
7
10

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.