Printing all filenames and number of lines/words

Hi, I'm trying to print all the name of the files in the working directory as well as the number of lines and words that each file has next to them

i.e

    file1.txt 71 431
    file2.bash 31 511


I tried using a script:
1
2
3
4
#!/bin/bash
ls * ;
wc -l ls *;
wc -w ls *;


But instead it prints

wc: ls: No such file or directory
  73 abc.txt
   5 cin.bash
  43 formula
   6 chem
 127 total
wc: ls: No such file or directory
 421 abc.txt
  12 cin.bash
 136 formula
  24 chem
 593 total



Can anyone tell me what I'm doing wrong or give some advice?
Last edited on
Advice: if you want to ask a question about scripting you might want to try and find a scripting forum, rather than a C++ forum :)

There are people on here that could help, but i'm just saying you might get more eyes on your problem on an appropriate forum.
You are asking to count the words in all the named files, including 'ls', which doesn't exist.
(Try creating a file named 'ls' to prove to yourself that it is the issue.)

The 'ls' command is for humans. The shell properly handles wildcards for you, so you don't need to try to insert a command to do it. Chances are it would produce results unusable for the command anyway.

Hope this helps.
man bash:
EXPANSION
Expansion is performed on the command line after it has been split into words. There are
seven kinds of expansion performed: brace expansion, tilde expansion, parameter and vari-
able expansion, command substitution, arithmetic expansion, word splitting, and pathname
expansion.

Pathname Expansion
After word splitting, unless the -f option has been set, bash scans each word for the
characters *, ?, and [. If one of these characters appears, then the word is regarded as
a pattern, and replaced with an alphabetically sorted list of file names matching the
pattern.

man wc:
NAME
       wc - print newline, word, and byte counts for each file

SYNOPSIS
       wc [OPTION]... [FILE]...

When you write wc * the wc never sees the *, unless bash fails to expand the word. What wc does see, is filenames. Note though that subdirectorynames are included.

One could control that with a loop:
for F in * ; do [[ -f "$F" ]] && wc -lw "$F"; done

C++ pseudo-equivalent:
1
2
3
4
5
for ( auto F : directorycontents ) {
  if ( isRegularFile( F ) ) {
    wc( F, WC::lines & WC::words );
  }
}


The other thing; you did desire "name lines words", but the wc shows "lines words name". Mere bash parameter expansion could do this, but there are other ways too:
wc -lw foo.txt | sed "s/ *\([^ ]\+\) *\([^ ]\+\) \(.*\)/\3 \t\2 \t\1/"
Hi, I'm trying to print all the name of the files in the working directory as well as the number of lines and words that each file has next to them

i.e
    file1.txt 71 431
    file2.bash 31 511


Isn't that being really fussy? You can swap the outputs with awk. Assuming the filenames don't have spaces:
 
wc -lw * | awk '{printf("%s %s %s\n", $3, $1, $2)}'
Last edited on
Registered users can post here. Sign in or register to post.