[comp.unix.shell] How to get AWK to output 2 fields at once

bill@twg.bc.ca (Bill Irwin) (10/29/90)

I  have what initially seemed to be a simple requirement:  get the  first
two fields from each line in file_1, and use them as a search pattern for
GREP to extract matching lines in file_2.  Sounds simple doesn't it?  Not
for  someone with very limited knowledge of AWK!  The first pass at  this
was:

for x in `cat file_1 | awk '{ print $1 " " $2 }'`
do
        grep "$x" file_2
done

Of course, the GREP routine executed with x having the value of the first
field  of  the  first line of file_1, then with the value of  the  second
field  of  the first line of file_1, then the first field of  the  second
line, .....

Is  there a way to get AWK to output "field_1 field_2" as the value of x,
so  that  this  can be used as the search pattern for GREP,  rather  than
"field_1" "field_2" "field_1" "field_2"?
-- 
Bill Irwin    -       The Westrheim Group     -    Vancouver, BC, Canada
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
uunet!van-bc!twg!bill     (604) 431-9600 (voice) |     UNIX Systems
bill@twg.bc.ca            (604) 430-4329 (fax)   |     Integration

jak9213@helios.TAMU.EDU (John Kane) (10/29/90)

In article <297@twg.bc.ca> bill@twg.bc.ca (Bill Irwin) writes:
>I  have what initially seemed to be a simple requirement:  get the  first
>two fields from each line in file_1, and use them as a search pattern for
>GREP to extract matching lines in file_2.  [...]

>for x in `cat file_1 | awk '{ print $1 " " $2 }'`
>do
>        grep "$x" file_2
>done

>Of course, the GREP routine executed with x having the value of the first
>field  of  the  first line of file_1, then with the value of  the  second
>field  of  the first line of file_1, then the first field of  the  second
>line, .....

>Is  there a way to get AWK to output "field_1 field_2" as the value of x,
>so  that  this  can be used as the search pattern for GREP,  rather  than
>"field_1" "field_2" "field_1" "field_2"?

Yep, There is.

for x in `cat file_1 | awk '{print "\"" $1 " " $2 "\"")'`
do
	grep "$x" file_2
done

Your problem was that you were just putting out the values as:
	field_1 field_2

By putting in the "\"" you are now getting:
	"field_1 field_2"

Hopefully this is what you need.

BTW, you can also do it:

awk '{ print "grep \"" $1 " " $2 "\" file_2" }' | sh

This outputs lines like:
	grep "field_1 field_2" file_2
	etc ...

I like to do it this way instead of the other, unless I need to do something
else with the "field_1 field_2" arguments, in addition to the grep.

-- 
 John Arthur Kane, Systems Analyst, Microcomputer Support and Training
 Texas A&M University, College Station, TX 77843  (409) 845-9999

 jak9213@helios.tamu.edu     profs: x043jk@tamvm1.tamu.edu

ronald@atcmp.nl (Ronald Pikkert) (10/29/90)

From article <297@twg.bc.ca>, by bill@twg.bc.ca (Bill Irwin):
<> 
<> Is  there a way to get AWK to output "field_1 field_2" as the value of x,
<> so  that  this  can be used as the search pattern for GREP,  rather  than
<> "field_1" "field_2" "field_1" "field_2"?

Your problem comes up AFTER awk. The for loop that you use
considers spaces to be field seperators and awk outputs spaces 
on your request.

You could do this:

cat file_1 | awk '{ print $1 " " $2 }' | while read x
do
        grep "$x" file_2
done

The read statement will leave the spaces in the awk output
unchanged.


-
Ronald Pikkert                 E-mail: ronald@atcmp.nl
@ AT Computing b.v.            Tel:    080 - 566880
Toernooiveld
6525 ED  Nijmegen

itkin@mrspoc.Transact.COM (Steven M. List) (10/30/90)

jak9213@helios.TAMU.EDU (John Kane) writes:

>In article <297@twg.bc.ca> bill@twg.bc.ca (Bill Irwin) writes:
>>I  have what initially seemed to be a simple requirement:  get the  first
>>two fields from each line in file_1, and use them as a search pattern for
>>GREP to extract matching lines in file_2.  [...]

>>for x in `cat file_1 | awk '{ print $1 " " $2 }'`
>>do
>>        grep "$x" file_2
>>done

>>Of course, the GREP routine executed with x having the value of the first
>>field  of  the  first line of file_1, then with the value of  the  second
>>field  of  the first line of file_1, then the first field of  the  second
>>line, .....

>>Is  there a way to get AWK to output "field_1 field_2" as the value of x,
>>so  that  this  can be used as the search pattern for GREP,  rather  than
>>"field_1" "field_2" "field_1" "field_2"?

>Yep, There is.

>for x in `cat file_1 | awk '{print "\"" $1 " " $2 "\"")'`
>do
>   grep "$x" file_2
>done

This seems a bit complicated, doesn't it?  How about:

    for x in "`cat file_1 | awk '{print $1, $2}'`"
    do
        grep "$x" file_2
    done

That is, why worry about the backslashes and quotes INSIDE AWK, when you
can put them outside?  Clean and simple!
-- 
 +----------------------------------------------------------------------------+
 :                Steven List @ Transact Software, Inc. :^>~                  :
 :           Chairman, Unify User Group of Northern California                :
 :     {apple,coherent,limbo,mips,pyramid,ubvax}!itkin@guinan.Transact.COM    :

engbert@cs.vu.nl (Engbert Gerrit IJff) (11/01/90)

In article <1990Oct29.171816.7459@mrspoc.Transact.COM>,
	itkin@mrspoc.Transact.COM (Steven M. List) writes:
) jak9213@helios.TAMU.EDU (John Kane) writes:
) 
) >In article <297@twg.bc.ca> bill@twg.bc.ca (Bill Irwin) writes:
) >>I  have what initially seemed to be a simple requirement:  get the  first
) >>two fields from each line in file_1, and use them as a search pattern for
) >>GREP to extract matching lines in file_2.  [...]
) 
) >>for x in `cat file_1 | awk '{ print $1 " " $2 }'`
) >>do
) >>        grep "$x" file_2
) >>done
) 
) >>Of course, the GREP routine executed with x having the value of the first
) >>field  of  the  first line of file_1, then with the value of  the  second
) >>field  of  the first line of file_1, then the first field of  the  second
) >>line, .....
) 
) >>Is  there a way to get AWK to output "field_1 field_2" as the value of x,
) >>so  that  this  can be used as the search pattern for GREP,  rather  than
) >>"field_1" "field_2" "field_1" "field_2"?
) 
) >Yep, There is.
) 
) >for x in `cat file_1 | awk '{print "\"" $1 " " $2 "\"")'`
) >do
) >   grep "$x" file_2
) >done
) 
) This seems a bit complicated, doesn't it?  How about:
) 
)     for x in "`cat file_1 | awk '{print $1, $2}'`"
)     do
)         grep "$x" file_2
)     done
) 
) That is, why worry about the backslashes and quotes INSIDE AWK, when you
) can put them outside?  Clean and simple!
) -- 

IMHO you will only get one x containing the whole awk output
and an this will cause the error message
	grep: illegal regular expression: No remembered search string.
However, using fgrep in your simple example works fine,
provided the whole construct is NOT meant to search for
regular expressions.

Bert.

lugnut@sequent.UUCP (Don Bolton) (11/14/90)

In article <1990Oct29.171816.7459@mrspoc.Transact.COM> itkin@guinan.Transact.COM writes:
>jak9213@helios.TAMU.EDU (John Kane) writes:
>
>>In article <297@twg.bc.ca> bill@twg.bc.ca (Bill Irwin) writes:
>>>I  have what initially seemed to be a simple requirement:  get the  first
>>>two fields from each line in file_1, and use them as a search pattern for
>>>GREP to extract matching lines in file_2.  [...]
>
>>>for x in `cat file_1 | awk '{ print $1 " " $2 }'`
>>>do
>>>        grep "$x" file_2
>>>done
>
>>>Of course, the GREP routine executed with x having the value of the first
>>>field  of  the  first line of file_1, then with the value of  the  second
>>>field  of  the first line of file_1, then the first field of  the  second
>>>line, .....
>
>>>Is  there a way to get AWK to output "field_1 field_2" as the value of x,
>>>so  that  this  can be used as the search pattern for GREP,  rather  than
>>>"field_1" "field_2" "field_1" "field_2"?
>
>>Yep, There is.
>
>>for x in `cat file_1 | awk '{print "\"" $1 " " $2 "\"")'`
>>do
>>   grep "$x" file_2
>>done
>
>This seems a bit complicated, doesn't it?  How about:
>
>    for x in "`cat file_1 | awk '{print $1, $2}'`"
>    do
>        grep "$x" file_2
>    done
>
>That is, why worry about the backslashes and quotes INSIDE AWK, when you
>can put them outside?  Clean and simple!

except the for statement still loops for EACH argument retrieved by your
awk statement. SOOOO... try

#Place in a _ to join $1 and $2 so the for loop sees a single arg

for x in `cat file_1 | awk '{print $1"_"$2}'`
    do

#Using the -F option for awk, remove the joiner for use by grep

	blarg=`echo $x | awk -F_ '{print $1, $2}'`
        grep $blarg file_2	
    done

Now you'll get what you want

lugnut@sequent.UUCP (Don Bolton) (11/14/90)

In article <46366@sequent.UUCP> lugnut@sequent.UUCP (Don Bolton) Will live
to regret writing :-)

>In article <1990Oct29.171816.7459@mrspoc.Transact.COM> itkin@guinan.Transact.COM writes:
>>jak9213@helios.TAMU.EDU (John Kane) writes:
>>
>>>In article <297@twg.bc.ca> bill@twg.bc.ca (Bill Irwin) writes:
>>>>I  have what initially seemed to be a simple requirement:  get the  first
>>>>two fields from each line in file_1, and use them as a search pattern for
>>>>GREP to extract matching lines in file_2.  [...]
>>
>>>>for x in `cat file_1 | awk '{ print $1 " " $2 }'`
>>>>do
>>>>        grep "$x" file_2
>>>>done
>>
>>>>Of course, the GREP routine executed with x having the value of the first
>>>>field  of  the  first line of file_1, then with the value of  the  second
>>>>field  of  the first line of file_1, then the first field of  the  second
>>>>line, .....
>>
>>>>Is  there a way to get AWK to output "field_1 field_2" as the value of x,
>>>>so  that  this  can be used as the search pattern for GREP,  rather  than
>>>>"field_1" "field_2" "field_1" "field_2"?
>>
>>>Yep, There is.
>>
>>>for x in `cat file_1 | awk '{print "\"" $1 " " $2 "\"")'`
>>>do
>>>   grep "$x" file_2
>>>done
>>
>>This seems a bit complicated, doesn't it?  How about:
>>
>>    for x in "`cat file_1 | awk '{print $1, $2}'`"
>>    do
>>        grep "$x" file_2
>>    done
>>
>>That is, why worry about the backslashes and quotes INSIDE AWK, when you
>>can put them outside?  Clean and simple!
>
>except the for statement still loops for EACH argument retrieved by your
>awk statement. SOOOO... try

OK I'm blind, missed the external " "s that you even mentioned. I hate
it when that happens.

So SHOOT ME NOW

<BOOM>

>#Place in a _ to join $1 and $2 so the for loop sees a single arg
>
>for x in `cat file_1 | awk '{print $1"_"$2}'`
>    do
>
>#Using the -F option for awk, remove the joiner for use by grep
>
>	blarg=`echo $x | awk -F_ '{print $1, $2}'`
>        grep $blarg file_2	
>    done
>
>Now you'll get what you want

Must be time for lunch.
certainly out to it anyways :-)