BASH and Shell Scripting

Reading From Files

How do you read a text file, line-by-line?

while IFS= read -r line; do echo $line; done < /path/to/file

The key is the read command.

To read the details of the read built-in, type help read in your terminal.



How do you find files by their inode number?

I have typically used this technique when I end up with some file that starts with a character that I can not use a mv, rm, or other standard command to work with.

First, do a listing of the directory as follows ls -li. This will display both the file an its inode. Once you have the inode, you can do a find by the inode number and then exec the command that you want to run on it.

find ./ -inum 1109845324 -exec ls {} \;

find … -print0 | xargs -0 otherwise if there are special chars in the results and you just find .. | xargs bad things can happen. (verify this)

grep (fgrep)

. find (1)
. Find to search for content in a file
find ./ -name ‘.html’ -type f | xargs egrep -i ‘@’ -l or find ./ -name ‘.html” -type f -exec egrep -i ‘@’ -l {} \;
or using regex
find ./ -regex ‘./.*.html’

    Prune example:

. xargs

    . xargs -L 1 tells it to run the command for each line in the stdin
    . cat someFile.txt | xargs -L 1 ./

    . If you are piping the output of find, which might have spaces in it,

xargs will split on the spaces, which isn’t what you want. In that case, you
need to use find with the -print0 option and invoke xargs with the -0 option
as in the following example:
$ find ./ -type f -print0 | xargs -0 grep ‘someString’

    . To run with multiple 'threads'
            $ seq 15 | xargs --max-procs=4 -n 1 echo

xargs -L 1 tells it to run the command for each line in the stdin

cat someFile.txt | xargs -L 1 ./

. seq:
. prints a sequence of numbers

. grep (1)
. print line numbers:
$ grep -n “foo” file.txt

    . print the negative result (lines that do not match)
            $ grep -vn "foo" file.txt

    . The only command of the three that supports backreferences and

saving in

. egrep
. extended grep (regexes)

. fgrep: fast grep, just string literals

. rename (1)
. sed
echo Sunday | sed ‘s/day/night’ => Sunnight


    . Search and replace files:

find ./ -type f -name ‘something’ | xargs sed -i ‘s/old/new’
find ./ -type f -name ‘something’ -exec sed -i ‘s/old/new’ {} \;

. awk

    . Basically used to render tabular data passed to it via STDIN
    . $1 refers to the first column

$ free -g | awk ‘{printf( “%s %sGB\n”, $1, $4)}’
total sharedGB
Mem: 13GB
-/+ 21GB
Swap: 25GB

. flex
. tr
. STDIN/STDOUT/STDERR and redirecting
. for loop:

    . for i in `ls /sbin`; do file /sbin/$i | grep 'symbolic'; done
    . for ((i=0; i<10; i+=1)); do echo $i; done

find: A good list of things you can do with find.



How do you declare a function that you can use in all of your terminal sessions

  • Add the func declaration to ~/.bash_profile or ~/.bashrc

How do you see the definition of any functions declared for your shell.

declare -f

See a specific one

declare -f <name-of-func>

stty What is this and how is it used.