6.Linux常用命令---文件目录管理(3)

发布于:2024-04-26 ⋅ 阅读:(26) ⋅ 点赞:(0)

6.37 read --读取标准输入命令

read内部命令被用来从标准输入读取单行数据。这个命令可以用来读取键盘输入,当使用重定向时,可以读取文件中的一行数据。

read a < 123.txt #读取文件123.txt中的内容,保存到变量a中

参数:
-a:后跟一个变量,该变量会被认为是个数组,然后给其赋值
-d:后面跟一个标识符,其实只有其后的第一个字符有用,作为结束的标志
-p:后面跟提示信息,即在输入前打印提示信息
-e:在输入的时候可以使用命令补全功能
-n:后跟一个数字,定义输入文本的长度
-r:屏蔽\,如果没有该选项,则\作为转义字符,有的话\就是个正常字符了。
-s:安静模式,在输入字符时不再屏幕上显示,例如login密码
-t:后面跟秒数,定义输入字符的等待时间
-u:后面跟fd,从文件描述符中读入,该文件描述符可以是excel新开启的

实例:

#提示符和用户输入不在同一行
#!/bin/bash
echo "输入网站名: "
#读取从键盘的输入,保存到一个变量中
read website
echo "你输入的网站名是 $website"
exit 0 #退出

#####################################
[root@localhost ~]# ./test1.sh 
输入网站名: 
www.baidu.com  #密码输入换行了,想要不换行,可以给echo加参数 echo -n "输入网站名: "

#或者如下
#####################################
#提示符和用户输入在同一行
#!/bin/bash
#读取从键盘的输入,保存到一个变量中
read  -p "enter a website: " website
echo "你输入的网站名是 $website"
exit 0 #退出

#####################################
[root@localhost ~]# ./test1.sh 
enter a website: www.baidu.com

-t参数指定read命令等待输入的秒数,当计时满时,read命令返回一个非零退出状态

#!/bin/bash
if read -t 5 -p "输入网站名:" website
then
	echo "你输入的网站名是 $website"
else
	echo -e "\n抱歉,你输入超时了。" #换行符可能不生效,加入-e参数,解析换行符
fi
exit 0
##############################################
[root@localhost ~]# ./test1.sh 
输入网站名:wwwwwwsds
抱歉,你输入超时了。

6.38 diff–比较文本差异

diff以逐行的方式,比较文本文件的异同处。如果指定要比较目录,则diff会比较目录中相同文件名的文件,但不会比较其中子目录。
参数
-<行数>  指定要显示多少行的文本。此参数必须与-c或-u参数一并使用。
-a或–text  diff预设只会逐行比较文本文件。
-b或–ignore-space-change  不检查空格字符的不同。
-B或–ignore-blank-lines  不检查空白行。
-c  显示全部内文,并标出不同之处。
-C<行数>或–context<行数>  与执行"-c-<行数>"指令相同。
-d或–minimal  使用不同的演算法,以较小的单位来做比较。
-e或–ed  此参数的输出格式可用于ed的script文件。
-f或-forward-ed  输出的格式类似ed的script文件,但按照原来文件的顺序来显示不同处。
-H或–speed-large-files  比较大文件时,可加快速度。
-l<字符或字符串>或–ignore-matching-lines<字符或字符串>  若两个文件在某几行有所不同,而这几行同时都包含了选项中指定的字符或字符串,则不显示这两个文件的差异。
-i或–ignore-case  不检查大小写的不同。
-l或–paginate  将结果交由pr程序来分页。
-n或–rcs  将比较结果以RCS的格式来显示。
-N或–new-file  在比较目录时,若文件A仅出现在某个目录中,预设会显示:
Only in目录:文件A若使用-N参数,则diff会将文件A与一个空白的文件比较。
-p  若比较的文件为C语言的程序码文件时,显示差异所在的函数名称。
-P或–unidirectional-new-file  与-N类似,但只有当第二个目录包含了一个第一个目录所没有的文件时,才会将这个文件与空白的文件做比较。
-q或–brief  仅显示有无差异,不显示详细的信息。
-r或–recursive  比较子目录中的文件。
-s或–report-identical-files  若没有发现任何差异,仍然显示信息。
-S<文件>或–starting-file<文件>  在比较目录时,从指定的文件开始比较。
-t或–expand-tabs  在输出时,将tab字符展开。
-T或–initial-tab  在每行前面加上tab字符以便对齐。
-u,-U<列数>或–unified=<列数>  以合并的方式来显示文件内容的不同。
-v或–version  显示版本信息。
-w或–ignore-all-space  忽略全部的空格字符。
-W<宽度>或–width<宽度>  在使用-y参数时,指定栏宽。
-x<文件名或目录>或–exclude<文件名或目录>  不比较选项中所指定的文件或目录。
-X<文件>或–exclude-from<文件>  您可以将文件或目录类型存成文本文件,然后在=<文件>中指定此文本文件。
-y或–side-by-side  以并列的方式显示文件的异同之处。
–help  显示帮助。
–left-column  在使用-y参数时,若两个文件某一行内容相同,则仅在左侧的栏位显示该行内容。
–suppress-common-lines  在使用-y参数时,仅显示不同之处。

实例1:比较两个文件

[root@localhost test3]# diff log2014.log log2013.log  
3c3
< 2014-03
---
> 2013-03
8c8
< 2013-07
---
> 2013-08
11,12d10
< 2013-11
< 2013-12

上面的"3c3"和"8c8"表示log2014.log和log20143log文件在3行和第8行内容有所不同;"11,12d10"表示第一个文件比第二个文件多了第11和12行。

实例2:并排格式输出

[root@localhost test3]# diff log2014.log log2013.log  -y -W 50            
2013-01                 2013-01
2013-02                 2013-02
2014-03               | 2013-03
2013-04                 2013-04
2013-05                 2013-05
2013-06                 2013-06
2013-07                 2013-07
2013-07               | 2013-08
2013-09                 2013-09
2013-10                 2013-10
2013-11               <
2013-12               <
[root@localhost test3]# diff log2013.log log2014.log  -y -W 50 
2013-01                 2013-01
2013-02                 2013-02
2013-03               | 2014-03
2013-04                 2013-04
2013-05                 2013-05
2013-06                 2013-06
2013-07                 2013-07
2013-08               | 2013-07
2013-09                 2013-09
2013-10                 2013-10
                      > 2013-11
                      > 2013-12

说明:

  • "|"表示前后2个文件内容有不同
  • "<"表示后面文件比前面文件少了1行内容
  • ">"表示后面文件比前面文件多了1行内容
diff test1 test2 | diffstat   //进行比较结果的统计显示

6.39 cut–剪切字段

参数:
-b:以字节单位进行分割,这些字节位置将忽略多字节字符边界,除非指定了-n标志
-c:以字符为单位进行分割
-d:自定义分隔符,默认为制表符
-f:通过指定哪一个字段进行提取。cut命令使用“TAB”作为默认的字段分隔符。
-n:取消分割多字节字符。仅和-b一起使用。如果字符的最后一个字节落在由-b标志的list参数指示的范围之内,该字符将被写出;否则,该字符将被移除。

实例:

[root@localhost ~]# cut -d ':' -f 1 /etc/passwd
root
bin
daemon
adm
lp
sync
shutdown

6.40 paste–合并文件

参数:
-d<间隔字符>或–delimiters=<间隔字符>  用指定的间隔字符取代跳格字符。
-s或–serial  串列进行而非平行处理。
–help  在线帮助。
–version  显示帮助信息。
[文件…] 指定操作的文件路径

实例
使用paste指令将文件"file"、“testfile”、"testfile1"进行合并,输入如下命令:
paste file testfile testfile1 #合并指定文件的内容
但是,在执行以上命令之前,首先使用"cat"指令对3个文件内容进行查看,显示如下所示:

//查看file文件内容
[root@localhost ~]# cat file
xiongdan 200   
lihaihui 233   
lymlrl 231 
//查看testfile文件的内容
[root@localhost ~]# cat testfile
liangyuanm  ss   
//查看testfile1文件的内容
[root@localhost ~]# cat testfile1
 huanggai 56   
 zhixi 73

当合并指令"$ paste file testfile testfile1"执行后,程序界面中将显示合并后的文件内容,如下所示:
xiongdan 200   
lihaihui 233   
lymlrl 231   
liangyuanm  ss   
huanggai 56   z
hixi 73

若使用paste指令的参数"-s",则可以将一个文件中的多行数据合并为一行进行显示。例如,将文件"file"中的3行数据合并为一行数据进行显示,输入如下命令

[root@localhost ~]# paste -s file             #合并指定文件的多行数据
上面的命令执行后,显示的数据内容如下所示:
xiongdan 200 lihaihui 233 lymlrl 231

注意:参数"-s"只是将testfile文件的内容调整显示方式,并不会改变原文件的内容格式。

6.41 tee–读取标准输入数据,并输出成文件

参数:
-a或–append  附加到既有文件的后面,而非覆盖它.
-i或–ignore-interrupts  忽略中断信号。
–help  在线帮助。
–version  显示版本信息。

#使用指令"tee"将用户输入的数据同时保存到文件"file1"和"file2"中,输入如下命令:
[root@host1 ~]# tee file1 file2                   #在两个文件中复制内容

#以上命令执行后,将提示用户输入需要保存到文件的数据,如下所示:
My Linux                        #提示用户输入数据  
My Linux                        #输出数据,进行输出反馈

此时,可以分别打开文件"file1""file2",查看其内容是否均是"My Linux"即可判断指令"tee"是否执行成功。

6.42 col–过滤控制字符

参数:
-b 过滤掉所有的控制字符,包括RLF和HRLF。
-f 滤除RLF字符,但允许将HRLF字符呈现出来。
-x 以多个空格字符来表示跳格字符。
-l<缓冲区列数> 预设的内存缓冲区有128列,您可以自行指定缓冲区的大小。

#将man 命令的帮助文档保存为man_help,使用-b 参数过滤所有控制字符。在终端中使用如下命令:
man man | col-b > man_help
#注:其中"|"用于建立管道,把man命令的输出结果转为col命令的输入数据。

6.43 comm–比较两个已排过序的文件

参数:
-1 不显示只在第1个文件里出现过的列。
-2 不显示只在第2个文件里出现过的列。
-3 不显示只在第1和第2个文件里出现过的列。

#aaa.txt 与 bbb.txt 的文件内容如下:
[root@localhost text]# cat aaa.txt
aaa
bbb
ccc
ddd
eee
111
222
[root@localhost text]# cat bbb.txt
bbb
ccc
aaa
hhh
ttt
jjj

#执行 comm 命令输出结果如下:
[root@localhost text]# comm aaa.txt bbb.txt
aaa
                bbb
                ccc
        aaa
ddd
eee
111
222
        hhh
        ttt
        jjj
#第一列  第二列  第三列
#输出的第一列只包含在aaa.txt中出现的行,第二列包含在bbb.txt中出现的行,第三列包含在aaa.txt和bbb.txt中相同的行。各列是以制表符(\t)作为定界符。

6.44 fmt–编排文本文件内容

参数:
-c或–crown-margin 每段前两列缩排。
-p<列起始字符串>或-prefix=<列起始字符串> 仅合并含有指定字符串的列,通常运用在程序语言的注解方面。
-s或–split-only 只拆开字数超出每列字符数的列,但不合并字数不足每列字符数的列。
-t或–tagged-paragraph 每列前两列缩排,但第1列和第2列的缩排格式不同。
-u或–uniform-spacing 每个字符之间都以一个空格字符间隔,每个句子之间则两个空格字符分隔。
-w<每行字符数>或–width=<每行字符数>或-<每行字符数> 设置每行的最大字符数。

#重排指定文件。如文件testfile共5 行文字,可以通过命令对该文件格式进行重排:
[root@host1 ~]# fmt testfile
hello Linux! Linux is a free Unix-type operating system. This is a  
Linux testfile! Linux Linux

#为了对比,先使用cat命令查看文件内容:
[root@host1 ~]# cat testfile
hello Linux!  
Linux is a free Unix-type operating system.  
This is a Linux testfile!  
Linux  
Linux

#使用fmt命令重排之后,指定重排宽度为85个字符:
[root@host1 ~]# fmt -w 85 testfile
hello Linux! Linux is a free Unix-type operating system. This is a Linux testfile!  
Linux Linux

6.45 join–将两个文件中,指定栏位内容相同的行连接起来

找出两个文件中,指定栏位内容相同的行,并加以合并,再输出到标准输出设备。

参数:
-a<1或2> 除了显示原来的输出内容之外,还显示指令文件中没有相同栏位的行。
-e<字符串> 若[文件1]与[文件2]中找不到指定的栏位,则在输出中填入选项中的字符串。
-i或–igore-case 比较栏位内容时,忽略大小写的差异。
-o<格式> 按照指定的格式来显示结果。
-t<字符> 指定栏位的分隔字符。
-v<1或2> 跟-a相同,但是只显示文件中没有相同栏位的行。
-1<栏位> 连接[文件1]指定的栏位。
-2<栏位> 连接[文件2]指定的栏位。

#首先查看testfile_1、testfile_2 中的文件内容:
[root@host1 ~]# cat testfile_1
Hello 95
Linux 85  
test 30  
[root@host1 ~]# cat testfile_2
Hello 2005
Linux 2009  
test 2006

#然后使用join命令,将两个文件连接,结果如下:
[root@host1 ~]# join testfile_1 testfile_2
Hello 95 2005
Linux 85 2009  
test 30 2006

#文件1与文件2的位置对输出到标准输出的结果是有影响的。例如将命令中的两个文件互换,最终在标准输出的输出结果将发生变化,如下所示:
[root@host1 ~]# join testfile_2 testfile_1
Hello 2005 95
Linux 2009 85  
test 2006 30

6.48 expr–手工命令行计数器,

表达式说明:

  • 用空格隔开每个项;
  • 用 / (反斜杠) 放在 shell 特定的字符前面;
  • 对包含空格和其他特殊字符的字符串要用引号括起来
//计算字串长度
> expr length “this is a test”
 14

//抓取字串
> expr substr “this is a test” 3 5
is is

//抓取第一个字符数字串出现的位置
> expr index "sarasara"  a
 2

//整数运算
> expr 14 % 9
 5
 > expr 10 + 10
 20
 > expr 1000 + 900
 1900
 > expr 30 / 3 / 2
 5
 > expr 30 /* 3 #(使用乘号时,必须用反斜线屏蔽其特定含义。因为shell可能会误解显示星号的意义)
 90
 > expr 30 * 3
 expr: Syntax error

6.49 dd–读取、转换并输出数据

参数:

  • if=文件名:输入文件名,缺省为标准输入。即指定源文件。
  • of=文件名:输出文件名,缺省为标准输出。即指定目的文件。
  • ibs=bytes:一次读入bytes个字节,即指定一个块大小为bytes个字节。
  • obs=bytes:一次输出bytes个字节,即指定一个块大小为bytes个字节。
  • bs=bytes:同时设置读入/输出的块大小为bytes个字节。
  • cbs=bytes:一次转换bytes个字节,即指定转换缓冲区大小。
  • skip=blocks:从输入文件开头跳过blocks个块后再开始复制。
  • seek=blocks:从输出文件开头跳过blocks个块后再开始复制。
  • count=blocks:仅拷贝blocks个块,块大小等于ibs指定的字节数。
  • conv=<关键字>,关键字可以有以下11种:
  • conversion:用指定的参数转换文件。
  • ascii:转换ebcdic为ascii
  • ebcdic:转换ascii为ebcdic
  • ibm:转换ascii为alternate ebcdic
  • block:把每一行转换为长度为cbs,不足部分用空格填充
  • unblock:使每一行的长度都为cbs,不足部分用空格填充
  • lcase:把大写字符转换为小写字符
  • ucase:把小写字符转换为大写字符
  • swab:交换输入的每对字节
  • noerror:出错时不停止
  • notrunc:不截短输出文件
  • sync:将每个输入块填充到ibs个字节,不足部分用空(NUL)字符补齐。
  • –help:显示帮助信息
  • –version:显示版本信息
#制作启动盘:
[root@host1 ~]# dd if=boot.img of=/dev/fd0 bs=1440k

#将testfile文件中的所有英文字母转换为大写,然后转成为testfile_1文件:
[root@host1 ~]# dd if=testfile_2 of=testfile_1 conv=ucase

#查看testfile_2:
[root@host1 ~]# cat testfile_2 
HELLO LINUX!  
Linux is a free unix-type opterating system.  
This is a linux testfile!  
Linux test

#转换完成后,使用dd 命令,大小写转换记录了0+1 的读入:
[root@host1 ~]# dd if=testfile_2 of=testfile_1 conv=ucase
记录了0+1 的写出
95字节(95 B)已复制,0.000131446 秒,723 KB/s
#查看转换后的testfile_1
[root@host1 ~]# cat testfile_1
HELLO LINUX!  
LINUX IS A FREE UNIX-TYPE OPTERATING SYSTEM.  
THIS IS A LINUX TESTFILE!  
LINUX TEST #testfile_2中的所有字符都变成了大写字母

#由标准输入设备读入字符串,并将字符串转换成大写后,再输出到标准输出设备:
[root@host1 ~]# dd conv=ucase

#输入以上命令后按回车键,输入字符串,再按回车键,按组合键Ctrl+D 退出,出现以下结果:
[root@host1 ~]# dd conv=ucase
Hello Linux! #输入字符串后按回车键  
HELLO LINUX! #按组合键Ctrl+D退出,转换成大写结果  
记录了0+1 的读入  
记录了0+1 的写出  
13字节(13 B)已复制,12.1558 秒,0.0 KB/s

6.50 EOF

EOF是END Of File的缩写,表示自定义终止符.既然自定义,那么EOF就不是固定的,可以随意设置别名,在linux按ctrl-d就代表EOF.EOF一般会配合cat能够多行文本输出.
其用法如下:

<<EOF        //开始
....
EOF            //结束

还可以自定义,比如自定义:

<<BBB        //开始
....
BBB              //结束

通过cat配合重定向能够生成文件并追加操作,在它之前先熟悉几个特殊符号:
< :输入重定向

:输出重定向

:输出重定向,进行追加,不会覆盖之前内容
<< :标准输入来自命令行的一对分隔号的中间内容.
先举一个简单的例子,例1:

# cat >> file << EOF
> Hello
> EOF
# cat << EOF > file
>Hello
>EOF

输入结束后,在终端显示以下内容:

 Hello 

6.51 basename–命令用于获取路径中的文件名或路径名

basename path
获取末尾的文件名或路径名

[root@host1 ~]# basename /etc/passwd
passwd

[root@host1 ~]# basename /etc/man.config
man.config

[root@host1 ~]# basename /etc/
etc

去掉末尾的指定字符
如果我们不需要扩展名或是末尾的子字符串的时候,第二个参数指定其即可取消。
取消扩展名

[root@host1 ~]# basename /etc/man.config
man.config

[root@host1 ~]# basename /etc/man.config .config
man

取消指定的字符
如下,要取消db.data,包括了扩展名在内

[root@host1 ~]# ls namedb.data
namedb.data
[root@host1 ~]# basename namedb.data db.data
name

6.52 uniq–去除连续的重复行

选项:
-i:忽略大小写
-c:统计重复行次数
-d:只显示重复行

6.53 paste–一列一列的合并

参数:
-d<间隔字符>或–delimiters=<间隔字符>  用指定的间隔字符取代跳格字符。
-s或–serial  串列进行而非平行处理。
–help  在线帮助。
–version  显示帮助信息。
[文件…] 指定操作的文件路径

实例
使用paste指令将文件"file"、“testfile”、"testfile1"进行合并:

[root@host1 test]# paste file testfile testfile1

[root@host1 test]# cat file
xiongdan 200  
lihaihui 233  
lymlrl 231  
[root@host1 test]# cat testfile
liangyuanm  ss  
[root@host1 test]# cat testfile1
huanggai 56  
zhixi 73

当合并指令"[root@host1 test]# paste file testfile testfile1"执行后,程序界面中将显示合并后的文件内容,如下所示:
xiongdan 200
lihaihui 233
lymlrl 231
liangyuanm ss
huanggai 56
zhixi 73

若使用paste指令的参数"-s",则可以将一个文件中的多行数据合并为一行进行显示。例如,将文件"file"中的3行数据合并为一行数据进行显示

[root@host1 test]# paste -s file

上面的命令执行后,显示的数据内容如下所示:
xiongdan 200 lihaihui 233 lymlrl 231
注意:参数"-s"只是将testfile文件的内容调整显示方式,并不会改变原文件的内容格式

6.54 tr–用于转换或删除,替换文件中的字符

#语法
tr [-cdst][--help][--version][第一字符集][第二字符集]  
tr [OPTION]…SET1[SET2]

#参数说明:
-c, --complement:反选设定字符。也就是符合 SET1 的部份不做处理,不符合的剩余部份才进行转换
-d, --delete:删除指令字符
-s, --squeeze-repeats:缩减连续重复的字符成指定的单个字符
-t, --truncate-set1:削减 SET1 指定范围,使之与 SET2 设定长度相等
--help:显示程序用法信息
--version:显示程序本身的版本信息

字符集合的范围:
\NNN 八进制值的字符 NNN (1 to 3 为八进制值的字符)
\ 反斜杠
\a Ctrl-G 铃声
\b Ctrl-H 退格符
\f Ctrl-L 走行换页
\n Ctrl-J 新行
\r Ctrl-M 回车
\t Ctrl-I tab键
\v Ctrl-X 水平制表符
CHAR1-CHAR2 :字符范围从 CHAR1 到 CHAR2 的指定,范围的指定以 ASCII 码的次序为基础,只能由小到大,不能由大到小。
[CHAR*] :这是 SET2 专用的设定,功能是重复指定的字符到与 SET1 相同长度为止
[CHAR*REPEAT] :这也是 SET2 专用的设定,功能是重复指定的字符到设定的 REPEAT 次数为止(REPEAT 的数字采 8 进位制计算,以 0 为开始)
[:alnum:] :所有字母字符与数字
[:alpha:] :所有字母字符
[:blank:] :所有水平空格
[:cntrl:] :所有控制字符
[:digit:] :所有数字
[:graph:] :所有可打印的字符(不包含空格符)
[:lower:] :所有小写字母
[:print:] :所有可打印的字符(包含空格符)
[:punct:] :所有标点字符
[:space:] :所有水平与垂直空格符
[:upper:] :所有大写字母
[:xdigit:] :所有 16 进位制的数字
[=CHAR=] :所有符合指定的字符(等号里的 CHAR,代表你可自订的字符)

#实例
testfile文件中的内容如下:
[root@host1 ~]# cat testfile         #testfile原来的内容  
Linux networks are becoming more and more common,
but scurity is often an overlooked  
issue. Unfortunately, in today’s environment all networks
are potential hacker targets,  
fro0m tp-secret military research networks to small home LANs.  
Linux Network Securty focuses on securing Linux in a
networked environment, where the  
security of the entire network needs to be considered
rather than just isolated machines.  
It uses a mix of theory and practicl techniques to
teach administrators how to install and  
use security applications, as well as how the
applcations work and why they are necesary.

使用 tr 命令大小写转换后,得到如下输出结果:
[root@host1 ~]# cat testfile | tr a-z A-Z #转换后的输出  
LINUX NETWORKS ARE BECOMING MORE AND MORE COMMON, BUT SCURITY IS OFTEN AN OVERLOOKED  
ISSUE. UNFORTUNATELY, IN TODAY’S ENVIRONMENT ALL NETWORKS ARE POTENTIAL HACKER TARGETS,  
FROM TP-SECRET MILITARY RESEARCH NETWORKS TO SMALL HOME LANS.  
LINUX NETWORK SECURTY FOCUSES ON SECURING LINUX IN A NETWORKED ENVIRONMENT, WHERE THE  
SECURITY OF THE ENTIRE NETWORK NEEDS TO BE CONSIDERED RATHER THAN JUST ISOLATED MACHINES.  
IT USES A MIX OF THEORY AND PRACTICL TECHNIQUES TO TEACH ADMINISTRATORS HOW TO INSTALL AND  
USE SECURITY APPLICATIONS, AS WELL AS HOW THE APPLCATIONS WORK AND WHY THEY ARE NECESARY.

输出结果如下:
[root@host1 ~]# cat testfile | tr [:lower:] [:upper:] #转换后的输出  
LINUX NETWORKS ARE BECOMING MORE AND MORE COMMON, BUT SCURITY IS OFTEN AN OVERLOOKED  
ISSUE. UNFORTUNATELY, IN TODAY’S ENVIRONMENT ALL NETWORKS ARE POTENTIAL HACKER TARGETS,  
FROM TP-SECRET MILITARY RESEARCH NETWORKS TO SMALL HOME LANS.  
LINUX NETWORK SECURTY FOCUSES ON SECURING LINUX IN A NETWORKED ENVIRONMENT, WHERE THE  
SECURITY OF THE ENTIRE NETWORK NEEDS TO BE CONSIDERED RATHER THAN JUST ISOLATED MACHINES.  
IT USES A MIX OF THEORY AND PRACTICL TECHNIQUES TO TEACH ADMINISTRATORS HOW TO INSTALL AND  
USE SECURITY APPLICATIONS, AS WELL AS HOW THE APPLCATIONS WORK AND WHY THEY ARE NECESARY.