If I issue the find command as follows:
find . -name *.ear It prints out:
./dir1/dir2/earFile1.ear ./dir1/dir2/earFile2.ear ./dir1/dir3/earFile1.ear I want to 'print' the name and the size to the command line:
./dir1/dir2/earFile1.ear 5000 KB ./dir1/dir2/earFile2.ear 5400 KB ./dir1/dir3/earFile1.ear 5400 KB 017 Answers
find . -name '*.ear' -exec ls -lh {} \; just the h extra from jer.drab.org's reply. saves time converting to MB mentally ;)
6You need to use -exec or -printf. Printf works like this:
find . -name *.ear -printf "%p %k KB\n" -exec is more powerful and lets you execute arbitrary commands - so you could use a version of 'ls' or 'wc' to print out the filename along with other information. 'man find' will show you the available arguments to printf, which can do a lot more than just filesize.
[edit] -printf is not in the official POSIX standard, so check if it is supported on your version. However, most modern systems will use GNU find or a similarly extended version, so there is a good chance it will be implemented.
6A simple solution is to use the -ls option in find:
find . -name \*.ear -ls That gives you each entry in the normal "ls -l" format. Or, to get the specific output you seem to be looking for, this:
find . -name \*.ear -printf "%p\t%k KB\n" Which will give you the filename followed by the size in KB.
1Using GNU find, I think this is what you want. It finds all real files and not directories (-type f), and for each one prints the filename (%p), a tab (\t), the size in kilobytes (%k), the suffix " KB", and then a newline (\n).
find . -type f -printf '%p\t%k KB\n' If the printf command doesn't format things the way you want, you can use exec, followed by the command you want to execute on each file. Use {} for the filename, and terminate the command with a semicolon (;). On most shells, all three of those characters should be escaped with a backslash.
Here's a simple solution that finds and prints them out using "ls -lh", which will show you the size in human-readable form (k for kilobytes and M for megabytes):
find . -type f -exec ls -lh \{\} \; As yet another alternative, "wc -c" will print the number of characters (bytes) in the file:
find . -type f -exec wc -c \{\} \; 3find . -name '*.ear' -exec du -h {} \; This gives you the filesize only, instead of all the unnecessary stuff.
2Awk can fix up the output to give just what the questioner asked for. On my Solaris 10 system, find -ls prints size in KB as the second field, so:
% find . -name '*.ear' -ls | awk '{print $2, $11}' 5400 ./dir1/dir2/earFile2.ear 5400 ./dir1/dir2/earFile3.ear 5400 ./dir1/dir2/earFile1.ear Otherwise, use -exec ls -lh and pick out the size field from the output. Again on Solaris 10:
% find . -name '*.ear' -exec ls -lh {} \; | awk '{print $5, $9}' 5.3M ./dir1/dir2/earFile2.ear 5.3M ./dir1/dir2/earFile3.ear 5.3M ./dir1/dir2/earFile1.ear Why not use du -a ? E.g.
find . -name "*.ear" -exec du -a {} \; Works on a Mac
1Try the following commands:
GNU stat:
find . -type f -name *.ear -exec stat -c "%n %s" {} ';' BSD stat:
find . -type f -name *.ear -exec stat -f "%N %z" {} ';' however stat isn't standard, so du or wc could be a better approach:
find . -type f -name *.ear -exec sh -c 'echo "{} $(wc -c < {})"' ';' I struggled with this on Mac OS X where the find command doesn't support -printf.
A solution that I found, that admittedly relies on the 'group' for all files being 'staff' was...
ls -l -R | sed 's/\(.*\)staff *\([0-9]*\)..............\(.*\)/\2 \3/' This splits the ls long output into three tokens
- the stuff before the text 'staff'
- the file size
- the file name
And then outputs tokens 2 and 3, i.e. output is number of bytes and then filename
8071 sections.php 54681 services.php 37961 style.css 13260 thumb.php 70951 workshops.php 1This should get you what you're looking for, formatting included (i.e. file name first and size afterward):
find . -type f -iname "*.ear" -exec du -ah {} \; | awk '{print $2"\t", $1}' sample output (where I used -iname "*.php" to get some result):
./plugins/bat/class.bat.inc.php 20K ./plugins/quotas/class.quotas.inc.php 8.0K ./plugins/dmraid/class.dmraid.inc.php 8.0K ./plugins/updatenotifier/class.updatenotifier.inc.php 4.0K ./index.php 4.0K ./config.php 12K ./includes/mb/class.hwsensors.inc.php 8.0K Just list the files (-type f) that match the pattern (-name '*.ear) using the disk-usage command (du -h) and sort the files by the human-readable file size (sort -h):
find . -type f -name '*.ear' -exec du -h {} \; | sort -h Output
5.0k ./dir1/dir2/earFile1.ear 5.4k ./dir1/dir2/earFile2.ear 5.4k ./dir1/dir3/earFile1.ear You could try this:
find. -name *.ear -exec du {} \; This will give you the size in bytes. But the du command also accepts the parameters -k for KB and -m for MB. It will give you an output like
5000 ./dir1/dir2/earFile1.ear 5400 ./dir1/dir2/earFile2.ear 5400 ./dir1/dir3/earFile1.ear find . -name "*.ear" | xargs ls -sh $ find . -name "test*" -exec du -sh {} \; 4.0K ./test1 0 ./test2 0 ./test3 0 ./test4 $ 0find . -name "*.ear" -exec ls -l {} \; If you need to get total size, here is a script proposal
#!/bin/bash totalSize=0 allSizes=`find . -type f -name *.ear -exec stat -c "%s" {} \;` for fileSize in $allSizes; do totalSize=`echo "$(($totalSize+$fileSize))"` done echo "Total size is $totalSize bytes" You could try for loop:
for i in `find . -iname "*.ear"`; do ls -lh $i; done