The grep command is used to search for text. The name "grep" means something like "general regular expression parser", and if you look at the grep man page it says "print lines matching a pattern". I always tell people that if they don't like the name "grep" they can think of it as "search" instead.
Basic grep
To look for the string foo in a file named bar use this command:
grep foo bar
That only looks for the lower-case string foo, so if you want to make it case-insensitive add the -i option, like this:
grep -i foo bar
That will find patterns like foo, Foo, or FOO (and others) in the file named bar.
If you want to search for the pattern foo in all files in the current directory use this command instead:
grep -i foo *
The output will show both the filename and the matching strings. If you just want to see the filenames use this command instead:
grep -il foo *
The -l option tells grep to just show the filenames, and not the matching patterns.
Pattern matching
Of course grep is much more powerful than this, and can handle very powerful regular expressions. In a simple example, suppose you want to search for the strings "Foo" or "Goo" in all files in the current directory. That command would be:
grep '[FG]oo' *
If you want to search for a sequence of three integers you might use a command like this:
grep '[0-9][0-9][0-9]' *
Regular expressions can get much, much more complicated (and powerful) than this, so I'll just leave it here for now.
Input streams
Because the grep command follows the normal STDIN/STDOUT model, you can use it to work with input streams as well as files. For instance, if you want to find all the Java processes running on your system you can use a command like this:
ps auxwww | grep -i java
In this example I've piped the output of the ps auxwww command into my grep command. The grep command only prints the lines that have the string "java" in them; all other lines from the ps command are not printed.
One way to find all the sub-directories in the current directory is to mix the ls and grep commands together, like this:
ls -al | grep '^d'
Here I'm using grep to list only those lines where the first character in the line is the letter d.
Power searching
A lot of times I know that the string "foo" exists in a file somewhere in my directory tree, but I can't remember where. In those cases I roll out this power command:
find . -type f -exec grep -il 'foo' {} \;
This is a special way of mixing the find and grep commands together to search every file in every subdirectory of my current location.
Note that on Mac OS X systems you may be able to use the mdfind command instead of this find/grep combination command. The mdfind command is a command-lind equivalent of the Spotlight search functionality.
Related commands
There are at least two other related commands that you should at least be aware of. The fgrep command stands for "fast grep", or "fixed strings", depending on who you talk to. The egrep command stands for "extended grep", and lets you use even more powerful regular expressions.
The strings command is good at finding printable strings in a binary file.
The locate command is more related to the find command, but I thought I would note that it is good at finding files in the entire filesystem when you know the filename, or part of the filename.
And as I mentioned in the previous section Mac OS X systems have the mdfind command. As a practical matter I use plain old grep 99% of the time.