1

I have to find all file types using file -b $(find . -type f), sort them into unique categories, and print out top 4 most categories where the number is replaced with equal number of "#". The output should look something like this:

 8 empty                      : ########
 6 ASCII text                 : ######
 3 Vim swap file, version 7.4 : ###
 1 UTF-8 Unicode text         : #

I can't figure out how to print out the number of files in each category as "#" marks.

I want get the number on each line as a value and put same amount of "#" marks at the end.

  • What did you try? – Satō Katsura Mar 25 '17 at 12:08
  • ↑ that doesn't sound anything like the question you've asked at the top. Please go back and edit the question to make it clear. – roaima Mar 25 '17 at 12:36
  • I have edited the question and i hope it is more understandable. – Buri Mar 25 '17 at 13:03
  • Yeah it is an assignment. I am totaly new to scripting so i am taking everything just if it works. Is there any better way to solve this? – Buri Mar 25 '17 at 13:06
  • I am allowed to use awk, but not perl. So can this be done by using awk? – Buri Mar 25 '17 at 13:20
0

To answer your main question "how to symbolize a number N with a sequence of N characters, here is a shell command that will do exactly that:

n=17          # Number to translate to a sequence
printf "%${n}s" '' | tr ' ' '#'

(alternate syntax: printf '%*s' "$n" '' | tr ' ' '#'; there are other alternatives, you get the idea)

What it does is generate a blank line made of n spaces (the printf part) and then convert each space to the desired character (the tr part).

Assuming you have a command count_files that output the list you have included in your question, this command may be used like this:

count_files \
| while read n type; do 
    printf '%4d %-30s %s\n' "$n" "$type" "$(printf "%${n}s" '' | tr ' ' '#')"
done

... and you will get this:

   8 empty                          ########
   6 ASCII text                     ######
   3 Vim swap file, version 7.4     ###
   1 UTF-8 Unicode text             #
0

In Perl, a character may be repeated a number of times using the x operator:

$ perl -e 'print "#" x 10, "\n"'
##########

Let's use that.

Rather than parsing the output of find:

find . -type f -exec file -b {} + | sort | uniq -c | sort -rn |
perl -ne 'chomp; s/\s+(\d+)\s+// && printf("%-3d %-50s: %s\n", $1, $_, "#" x $1)'

The first part, up until the Perl script, will produce output like

  23 ASCII C program text
  12 ASCII text
  10 ELF 64-bit LSB relocatable, x86-64, version 1
   3 ASCII English text
   1 ELF 64-bit LSB shared object, x86-64, version 1

The Perl script will remove the trailing newline with chomp and then pick out the number into $1. It then uses printf() to print out the number, file type, and as many # characters as indicated by the number.

The final output will be something like

23  ASCII C program text                              : #######################
12  ASCII text                                        : ############
10  ELF 64-bit LSB relocatable, x86-64, version 1     : ##########
3   ASCII English text                                : ###
1   ELF 64-bit LSB shared object, x86-64, version 1   : #

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.