Learning AWK, slightly confused 
Author Message
 Learning AWK, slightly confused

All,

I am a brand new AWK user, and am trying to do something.
Im kinda at the point where I know what i want to get done,
and Im pretty sure AWK can do it, im just not certain how...

In any case, Ive cobbled together the following bad example:

/usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {

        if (substr($9,1,1) == K || substr($9,1,1) == S){
                if (substr($1,1,1) == l) {
                        print $9 $10 $11
                } else {
                        print $9
                }      
        }        
    }                  

Quote:
}'

I get an error right near line 1.  Im sure this is totally
wrong, but I don't have a book on AWK (yet) and jumped right into
the fire based on some web examples.  

What Im trying to do is take a long directory listing of my rc
scripts.  If they are active (K or S as the first char in their
name), then I want to print out the file name.  I check to see if
they are a symlink, and either way print out the name.  

Simple task, and I could do it really easily in Perl, but
Perl isn't installed (read isn't allowed), so Im stuck using
ksh and AWK.  Any pointers?

TIA

-DS



Sat, 09 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused

   >All,
   >I am a brand new AWK user, and am trying to do something.
   >Im kinda at the point where I know what i want to get done,
   >and Im pretty sure AWK can do it, im just not certain how...
   >In any case, Ive cobbled together the following bad example:
   >/usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {
   >if (substr($9,1,1) == K || substr($9,1,1) == S){
   >if (substr($1,1,1) == l) {
   >print $9 $10 $11
   >} else {
   >print $9
   >}
   >}
   >}
   >}'
   >I get an error right near line 1.  Im sure this is totally
   >wrong, but I don't have a book on AWK (yet) and jumped right into
   >the fire based on some web examples.
When you use a pipe or redirection inside an awk script, the command or
filename must be in quotes or in a variable, like:
while( "/usr/bin/ls -l /etc/rc2.d" | getline )
I would do the piping outside of awk, but that's just a matter of personal
preference.

Net-Tamer V 1.08X - Test Drive



Sat, 09 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused


Quote:
>All,

>I am a brand new AWK user, and am trying to do something.
>Im kinda at the point where I know what i want to get done,
>and Im pretty sure AWK can do it, im just not certain how...

>In any case, Ive cobbled together the following bad example:

>/usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {

>    if (substr($9,1,1) == K || substr($9,1,1) == S){
>            if (substr($1,1,1) == l) {
>                    print $9 $10 $11
>            } else {
>                    print $9
>            }      
>    }        
>    }                      
>}'

>I get an error right near line 1.  Im sure this is totally
>wrong, but I don't have a book on AWK (yet) and jumped right into
>the fire based on some web examples.  

>What Im trying to do is take a long directory listing of my rc
>scripts.  If they are active (K or S as the first char in their
>name), then I want to print out the file name.  I check to see if
>they are a symlink, and either way print out the name.  

>Simple task, and I could do it really easily in Perl, but
>Perl isn't installed (read isn't allowed), so Im stuck using
>ksh and AWK.  Any pointers?

1. pipe the output of your ls into awk.
2. double quote literal strings, otherwise awk thinks they are
   variable names.
3. separate parameters in a print statement to use the FS, otherwise
   the output will be pasted together without a FS (field separator).
4. get the curly brackets to match properly.

   Here's how I'd rewrite your script:

/usr/bin/ls -l /etc/rc2.d |
awk '{if (substr($9,1,1) == "K" || substr($9,1,1) == "S"){
                if (substr($1,1,1) == "l") {print $9, $10, $11}
                else {print $9} } }'

but this is more in awk's style:

/usr/bin/ls -l /etc/rc2.d |
awk 'substr($9,1,1) == "K" || substr($9,1,1) == "S"{
          if (substr($1,1,1) == "l") { print $9, $10, $11 }
          else {print $9} }'

or perhaps like this:

/usr/bin/ls -l /etc/rc2.d |
awk '/^l/ && ($9 ~ /^K/ || $9 ~ /^S/) {print $9, $10, $11; next}
              $9 ~ /^K/ || $9 ~ /^S/  {print $9}'

or using the ? : operator you could write this:

/usr/bin/ls -l /etc/rc2.d |
awk '$9 ~ /^K/ || $9 ~ /^S/ {
          print ($1 ~ /^l/) ? $9 " " $10 " " $11 : $9}'

Chuck Demas
Needham, Mass.

--
  Eat Healthy    |   _ _   | Nothing would be done at all,

  Die Anyway     |    v    | That no one could find fault with it.



Sun, 10 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused


% In any case, Ive cobbled together the following bad example:
%
% /usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {

This should be
 "/usr/bin/ls -l /etc/rc2.d" | getline

I like to test for > 0, since I have a suspicion getline can return -1
under some circumstance.

If your shell script runs only awk, I think it makes sense to do the
whole thing as a pure awk script:
 #!/usr/bin/awk -f
 BEGIN {
    while ("ls -l /etc/rc2.d" | getline > 0) {
       if ($9 ~ /^[KS]/) {
          if ($1 ~ /^l/) print $9,$10,$11
          else print $9
       }

    }

You could also let the sub-shell filter out the scripts you want
(ls -l /etc/rc2.d/[KS]*) and just look for links with awk.

% wrong, but I don't have a book on AWK (yet) and jumped right into
% the fire based on some web examples.  

You should get the gawk manual (which is part of the gawk distribution,
which is available wherever GNU software is sold).

--

Patrick TJ McPhee
East York  Canada



Sun, 10 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused

% If your shell script runs only awk, I think it makes sense to do the
% whole thing as a pure awk script:
%  #!/usr/bin/awk -f
%  BEGIN {
%     while ("ls -l /etc/rc2.d" | getline > 0) {
%        if ($9 ~ /^[KS]/) {
%           if ($1 ~ /^l/) print $9,$10,$11
%           else print $9
%        }
%          
%     }

   }

But I suggest you add one more brace so there's no syntax error (sorry).
--

Patrick TJ McPhee
East York  Canada



Sun, 10 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused

Quote:



>>All,

>>I am a brand new AWK user, and am trying to do something.
>>Im kinda at the point where I know what i want to get done,
>>and Im pretty sure AWK can do it, im just not certain how...

>>In any case, Ive cobbled together the following bad example:

>>/usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {

>>        if (substr($9,1,1) == K || substr($9,1,1) == S){
>>                if (substr($1,1,1) == l) {
>>                        print $9 $10 $11
>>                } else {
>>                        print $9
>>                }      
>>        }        
>>    }                  
>>}'
[snip]

>/usr/bin/ls -l /etc/rc2.d |
>awk '$9 ~ /^K/ || $9 ~ /^S/ {
>      print ($1 ~ /^l/) ? $9 " " $10 " " $11 : $9}'

Better still (as Patrick suggested) is:

/usr/bin/ls -l /etc/rc2.d |
awk '$9 ~ /^[KS]/ {print ($1 ~ /^l/) ? $9 " " $10 " " $11 : $9}'

Chuck Demas
Needham, Mass.

--
  Eat Healthy    |   _ _   | Nothing would be done at all,

  Die Anyway     |    v    | That no one could find fault with it.



Sun, 10 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused

Better still (as Patrick suggested) is:

/usr/bin/ls -l /etc/rc2.d |
awk '$9 ~ /^[KS]/ {print ($1 ~ /^l/) ? $9 " " $10 " " $11 : $9}'

In case anyone's interested, here's a one-liner which will probably work
in a ksh without awk:

ls -l `grep -lE "^K|^S" /etc/rc2.d/*` | tr -s " " | cut -d " " -f9,10,11

Cheers,
Steve

Western Geophysical, Bedford, UK
Tel: +44 (0) 1234 224404
Fax: +44 (0) 1234 224517



Sun, 10 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused

Quote:

> In case anyone's interested, here's a one-liner which will probably work
> in a ksh without awk:

> ls -l `grep -lE "^K|^S" /etc/rc2.d/*` | tr -s " " | cut -d " " -f9,10,11

wow.  I'm gathering that the Perl motto (Theres More Than One Way To
Do It) could be applied to AWK and ksh as well.  I wish I could find
a nice, functional, language where there _is_ only one way to do
something.  Id have more hair =)  

Thanks to all who have posted and emailed some great examples.
You've been most helpfull.



Sun, 10 Nov 2002 03:00:00 GMT  
 Learning AWK, slightly confused

Quote:

> /usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {

>    if (substr($9,1,1) == K || substr($9,1,1) == S){
>            if (substr($1,1,1) == l) {
>                    print $9 $10 $11
>            } else {
>                    print $9
>            }      
>    }        
>     }                      
> }'

> I get an error right near line 1.

You need to put your literal strings in double quotes, i.e.

 /usr/bin/awk '{while("/usr/bin/ls -l /etc/rc2.d" | getline ) {

and the same for the "K", "S" and "l" literals.
Your line
                        print $9 $10 $11
probably should be
                        print $9,$10,$11
to seperate the three strings from each other with a space
(=default value of OFS).
And you don't need that while() loop in Awk, you can pipe the output of
"ls" right into your Awk script (it's just like perl -n). If you want to
keep the while loop, you have to put it in the BEGIN block of your
script, or else your while loop will be executed for every line that
comes into stdin. So, instead of

Quote:
> /usr/bin/awk '{while( /usr/bin/ls -l /etc/rc2.d | getline ) {

use

  /usr/bin/awk 'BEGIN {while( "/usr/bin/ls -l /etc/rc2.d" | getline ) {

or just

  /usr/bin/ls -l /etc/rc2.d | /usr/bin/awk '{

and drop the corresponding "}", too.

Quote:
>  Im sure this is totally
> wrong, but I don't have a book on AWK (yet) and jumped right into
> the fire based on some web examples.  

Maybe you can find the GNU Awk manual, "Effective AWK Programming", in
HTML form. It is very good and has many examples.

If you are on Solaris, use "nawk" instead of "awk". "awk" on Solaris is
an ancient version of Awk.

Regards...
                Michael



Sun, 10 Nov 2002 03:00:00 GMT  
 
 [ 9 post ] 

 Relevant Pages 

1. Confused by awk version

2. confused if i should be doing type checking in the code ( a confused java programmer)

3. confused if i should be doing type checking in the co de ( a confused java programmer)

4. Learning Arrays in AWK

5. Sites for learning AWK

6. Newbie question: how to learn (N)AWK

7. learning awk (newbie)

8. Learning AWK...

9. FAQ: How can I learn awk?

10. Awk, SH, Perl -- Worth learning?

11. learning awk

12. Learn awk before perl?

 

 
Powered by phpBB® Forum Software