Wow!! Well have you tried
RUNNING the commands to see what happens?
What that command is SUPPOSED to do is find ALL files in /, runs the file command to find out the type of file, uses grep to find results containing the string "Shell script" and then counts the number of results returned by grep.
So in other words, it SHOULD determine the number of shell-scripts you have on your PC.
In answer to the questions:
1. The quotes
aren't required around the
{}
braces. The find command with the
-exec
will work with, or without quotes around the braces.
The
{}
braces are a placeholder for the path/file that was found by
find
, which will be substituted into
find
's
-exec
command each time
find
"finds" a file.
2.
-exec
expects a semi-colon that has been escaped by a backslash
\
character e.g.
\;
To indicate the end of the command that is to be executed each time a file is found.
If you leave the
\
(escape character) out - the semi-colon
;
gets treated as a literal semi-colon character. So you'll get a syntax error because
-exec
has not been terminated correctly and it will affect the shells interpretation of the rest of the line.
3. If you left the quotes out of the
'Shell script'
parameter to
grep
- then in the
grep
command, the space would be interpreted as a literal space, so the shell would treat the words "Shell" and "script" as separate entities.
In other words - in the context of the
grep
command:
"Shell" would be the search term and the word "script" would be the file (or directory) for
grep
to search in. AND on top of that you're getting the filename from
find
piped into the end of the
grep
command too.
So you'll at least get an error about a file/directory called script not existing. UNLESS you have a file, or directory called script in the current working directory. In which case - grep may or may not get a result, depending on whether the script file/directory contains anything with the word "Shell" anywhere in it.
So in the
grep
command, the quotes are required because the space character in "Shell script" is part of the search term.
Note: When quoting, you can use single quotes, or double quotes.
The difference between single quotes and double quotes are - strings inside single quotes are literal strings.
Strings that are inside double quotes can use shell expansions - e.g. variable substitutions, command substitutions, arithmetic substitutions. So by using double quotes you can build strings using values from variables, or using the output of other commands.
It is also possible to include the space in the search
without using the quotes - by escaping any space characters with a
\
backslash.
e.g.
Bash:
sudo find / -type f -exec file {} \; | grep Shell\ script | wc -l
FINALLY - your original command
WILL run without any errors, but it should be noted that it will almost certainly return an incorrect count of 0. Which is probably a deliberate bug put in by your professor (or perhaps it was just a typo on your part?!).
Here is your original command again:
Bash:
sudo find / -type f -exec file ’{}’ \; | grep ’Shell script’ | wc -l
Why do I know it will return 0? Because if you run the
file
command on a bash shell-script it says:
"/path/to/filename: Bourne-Again shell script, ASCII text executable"
Your
grep
command is searching for "Shell script" NOT "shell script". And by default,
grep
s searches are case-sensitive. So because of the capital S - you'll get no matches. And because there are no matches from
grep
-
wc
will return a count of 0; Which is incorrect!
So in order to get any positive results from
grep
- you either need to use
grep
s -i option, or change the uppercase S at the start of the search term, to a lower-case s.
So in order to get the intended output - the correct command should be either:
Bash:
sudo find / -type f -exec file {} \; | grep -i 'Shell script' | wc -l
OR:
Bash:
sudo find / -type f -exec file {} \; | grep -i "Shell script" | wc -l
OR:
Bash:
sudo find / -type f -exec file {} \; | grep -i Shell\ script | wc -l
OR:
Bash:
sudo find / -type f -exec file {} \; | grep 'shell script' | wc -l
OR:
Bash:
sudo find / -type f -exec file {} \; | grep "shell script" | wc -l
OR:
Bash:
sudo find / -type f -exec file {} \; | grep shell\ script | wc -l
All of the above commands are equivalent and should yield the same result, which will be the number of shell-scripts on the current system.
The first three use
grep
's case-insensitive search. The last three specify the all lower-case "shell script".
And the only other differences are the quoting methods used. Single quotes, double quotes and no-quotes (but escaping space characters).
I hope this clears things up for you!