⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ch16.htm

📁 《Perl 5 Unreleased》
💻 HTM
📖 第 1 页 / 共 5 页
字号:
<P>

Multiple parameters are specified using a syntax similar to a

Perl program. For example, consider the following statement:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">#define POW(base, power) ((base) ** (power))

<BR>

$result = POW(2,3);</FONT></TT>

</BLOCKQUOTE>

<P>

It produces this result:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">$result = ((2) ** (3));</FONT></TT>

</BLOCKQUOTE>

<P>

Macros can be reused. For example,

<BLOCKQUOTE>

<TT><FONT FACE="Courier">#define PI  3.141<BR>

#define AREA(rad)  (2* (rad) * PI)<BR>

$result = 43 + AREA($radius);</FONT></TT>

</BLOCKQUOTE>

<P>

Here, the macro <TT><FONT FACE="Courier">PI</FONT></TT> is defined

first, the macro <TT><FONT FACE="Courier">AREA</FONT></TT> uses

<TT><FONT FACE="Courier">PI</FONT></TT> to return an area for

a given radius in <TT><FONT FACE="Courier">$</FONT></TT>. 

<H3><A NAME="UsingthenandpOptionsforHandling">Using the <TT><FONT SIZE=4 FACE="Courier">-n</FONT></TT><FONT SIZE=4>

and </FONT><TT><FONT SIZE=4 FACE="Courier">-p</FONT></TT><FONT SIZE=4>

Options for Handling Multiple Files</FONT></A></H3>

<P>

When processing input from multiple files, it's often convenient

to put the processing function in a <TT><FONT FACE="Courier">while(&lt;&gt;)</FONT></TT>

loop so that each line in each file is sequentially processed.

For example, you'll see code of the following form: 

<BLOCKQUOTE>

<TT><FONT FACE="Courier">while ($line = &lt;&gt;) {<BR>

&nbsp;&nbsp;&amp;processMe($line)<BR>

}</FONT></TT>

</BLOCKQUOTE>

<P>

Use the <TT><FONT FACE="Courier">-n</FONT></TT> option to not

specify the <TT><FONT FACE="Courier">while</FONT></TT> loop. This

option forces Perl to take your program and execute it once for

each line of input in each of the files specified on the command

line. Here's an example:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">#!perl -n<BR>

$line = $_;<BR>

chop ($line);<BR>

printf (&quot;%d %-52s *\n&quot;, $ctr++, $line);</FONT></TT>

</BLOCKQUOTE>

<P>

The <TT><FONT FACE="Courier">-n</FONT></TT> option encloses this

program in an invisible <TT><FONT FACE="Courier">while</FONT></TT>

loop. Each line of input is stored in the system variable <TT><FONT FACE="Courier">$_</FONT></TT>

by the Perl interpreter, which then calls this program. The same

program could be rewritten as follows: 

<BLOCKQUOTE>

<TT><FONT FACE="Courier">#!perl<BR>

while (&lt;&gt;) {<BR>

$line = $_;<BR>

chop ($line);<BR>

printf (&quot;%d %-52s *\n&quot;, $ctr++, $line);<BR>

}</FONT></TT>

</BLOCKQUOTE>

<P>

The <TT><FONT FACE="Courier">-n</FONT></TT> and <TT><FONT FACE="Courier">-e</FONT></TT>

options can be used together to perform a function on each line

of input of all input files. For example, the following statements

both search for the word <TT><FONT FACE="Courier">param</FONT></TT>

in all files whose names end with <TT><FONT FACE="Courier">.pl</FONT></TT>:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -n -e &quot;print $_ if (/param/);&quot;

*.pl<BR>

<BR>

grep &quot;param&quot; *.pl</FONT></TT>

</BLOCKQUOTE>

<P>

The <TT><FONT FACE="Courier">print $_ if (/param/);</FONT></TT>

argument supplied with the <TT><FONT FACE="Courier">-e</FONT></TT>

option is a one-line Perl program that prints the current line

if the word<I> </I><TT><FONT FACE="Courier">param</FONT></TT>

is found in it. The <TT><FONT FACE="Courier">-n</FONT></TT> option

executes the one-line program once for each input line that is

set into the system variable <TT><FONT FACE="Courier">$_</FONT></TT>.

<P>

The <TT><FONT FACE="Courier">-p</FONT></TT> option is like the

<TT><FONT FACE="Courier">-n </FONT></TT>option except that it

prints each line as it reads each line. The <TT><FONT FACE="Courier">-p</FONT></TT>

option is designed for use with the <TT><FONT FACE="Courier">-i</FONT></TT>

option, which is described in the following section. If both the

<TT><FONT FACE="Courier">-p</FONT></TT> and the <TT><FONT FACE="Courier">-n</FONT></TT>

options are specified, the <TT><FONT FACE="Courier">-n</FONT></TT>

option is ignored.

<H3><A NAME="TheiOptiontoEditFiles">The <TT><FONT SIZE=4 FACE="Courier">-i</FONT></TT><FONT SIZE=4>

Option to Edit Files</FONT></A></H3>

<P>

Both the <TT><FONT FACE="Courier">-n</FONT></TT> and <TT><FONT FACE="Courier">-p</FONT></TT>

options read lines from the files whose names are listed on the

command line. When the <TT><FONT FACE="Courier">-i</FONT></TT>

option is used with the <TT><FONT FACE="Courier">-p</FONT></TT>

option, the Perl interpreter takes the input lines being read

and writes them back out to the files from which they came. For

example, consider the following command:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -p -i -e &quot;s/Costa/Rica/g;&quot;

*.txt</FONT></TT>

</BLOCKQUOTE>

<P>

It replaces every instance of <TT><FONT FACE="Courier">Costa</FONT></TT>

with <TT><FONT FACE="Courier">Rica</FONT></TT> in all the files

whose names end with <TT><FONT FACE="Courier">.txt</FONT></TT>.

<P>

<CENTER>

<TABLE BORDERCOLOR=#000000 BORDER=1 WIDTH=80%>

<TR VALIGN=TOP><TD ><B>Caution</B></TD></TR>

<TR VALIGN=TOP><TD >

<BLOCKQUOTE>

Do not use the <TT><FONT FACE="Courier">-i</FONT></TT> option with the <TT><FONT FACE="Courier">-n</FONT></TT> option. The following command:

</BLOCKQUOTE>

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -n -i -e &quot;s/Stock/Option/g;&quot; *.txt</FONT></TT>

</BLOCKQUOTE>

<BLOCKQUOTE>

also changes all occurrences of <TT><FONT FACE="Courier">Stock</FONT></TT> to <TT><FONT FACE="Courier">Option</FONT></TT>. However, it does <I>not</I> write out the input lines after it changes them! Because the <TT><FONT FACE="Courier">-i</FONT></TT> 

option forces the input files to be written to and nothing is printed, you'll erase the contents of all the files with <TT><FONT FACE="Courier">.txt</FONT></TT> extensions!

</BLOCKQUOTE>



</TD></TR>

</TABLE></CENTER>

<P>

<P>

The <TT><FONT FACE="Courier">-i</FONT></TT> option does not have

to work in conjunction with the <TT><FONT FACE="Courier">-p</FONT></TT>

option if the program that uses the option contains the <TT><FONT FACE="Courier">&lt;&gt;</FONT></TT>

operator inside a loop. For example, consider the following command:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -i *.txt</FONT></TT>

</BLOCKQUOTE>

<P>

It will copy the content of each input file to a temporary file

and then open it for reading. The input file is closed and then

reopened for writing. This process is repeated for all input files.

<P>

Listing 16.1 presents a simple example of a program using both

the <TT><FONT FACE="Courier">-i</FONT></TT> option and the <TT><FONT FACE="Courier">&lt;&gt;</FONT></TT>

operator. This program replaces all occurrences of <TT><FONT FACE="Courier">Wall</FONT></TT>

with <TT><FONT FACE="Courier">Brick</FONT></TT>.

<HR>

<BLOCKQUOTE>

<B>Listing 16.1. A program that edits files using the </B><TT><B><FONT FACE="Courier">-i</FONT></B></TT><B>

option.<BR>

</B>

</BLOCKQUOTE>

<BLOCKQUOTE>

<TT><FONT FACE="Courier">1 #!perl -I<BR>

2 while ($line = &lt;&gt;) {<BR>

3 $line =~ s/Wall/Brick/g;<BR>

4&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;print ($line);

<BR>

5 }</FONT></TT>

</BLOCKQUOTE>

<HR>

<P>

No output is sent to the screen because the output is redirected

to each input file. 

<P>

The <TT><FONT FACE="Courier">-i</FONT></TT> option can be used

to back up input files, too. By specifying a new file extension

to the <TT><FONT FACE="Courier">-i</FONT></TT> option, you can

ask that the new extension be appended to the filename being written

to. For example, the following command: 

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -i .bak dog mouse</FONT></TT>

</BLOCKQUOTE>

<P>

will result in two extra files, <TT><FONT FACE="Courier">dog.bak</FONT></TT>

and <TT><FONT FACE="Courier">mouse.bak</FONT></TT>, being written

to disk. The <TT><FONT FACE="Courier">.bak</FONT></TT> file extension

specified with <TT><FONT FACE="Courier">-i</FONT></TT> will force

the Perl interpreter to copy each <TT><I><FONT FACE="Courier">file</FONT></I></TT>

to <TT><I><FONT FACE="Courier">file.bak</FONT></I></TT> before

overwriting it. 

<H3><A NAME="UsingtheaOption">Using the <TT><FONT SIZE=4 FACE="Courier">-a</FONT></TT><FONT SIZE=4>

Option</FONT></A></H3>

<P>

The <TT><FONT FACE="Courier">-a</FONT></TT> option is used for

extracting words from files. The <TT><FONT FACE="Courier">-a</FONT></TT>

option is designed to be used with the <TT><FONT FACE="Courier">-n</FONT></TT>

or <TT><FONT FACE="Courier">-p</FONT></TT> option to split incoming

lines into a list of items in the <TT><FONT FACE="Courier">@F</FONT></TT>

array. Each item in the <TT><FONT FACE="Courier">@F</FONT></TT>

array is a word derived by applying the <TT><FONT FACE="Courier">split('

',$_)</FONT></TT> function to each input line. For example, if

your input file contains the following line:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">My name is&nbsp;&nbsp;&nbsp;&nbsp; Kamran

</FONT></TT>

</BLOCKQUOTE>

<P>

the result of the <TT><FONT FACE="Courier">-a</FONT></TT> option

that reads this line sets the contents of the array <TT><FONT FACE="Courier">@F</FONT></TT>

to be the following list:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">(&quot;My&quot;, &quot;name&quot;, &quot;is&quot;,

&quot;Kamran&quot;)</FONT></TT>

</BLOCKQUOTE>

<P>

Note that extraneous spaces and tabs from the input line have

not been added to the <TT><FONT FACE="Courier">@F</FONT></TT>

array. 

<P>

Listing 16.2 shows a sample program of how to use the <TT><FONT FACE="Courier">-a</FONT></TT>

option to extract all numeric values that are the first word of

an input line. 

<HR>

<BLOCKQUOTE>

<B>Listing 16.2. Sample use of the </B><TT><B><FONT FACE="Courier">-a</FONT></B></TT><B>

option.<BR>

</B>

</BLOCKQUOTE>

<BLOCKQUOTE>

<TT><FONT FACE="Courier">1&nbsp;&nbsp;#!perl -a -n<BR>

2&nbsp;&nbsp;while ($F[0] =~ /[^\d.]/) {<BR>

3&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;shift

(@F);<BR>

4&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;next

if (!defined($F[0]));<BR>

5&nbsp;&nbsp;}<BR>

6&nbsp;&nbsp;print (&quot;$F[0] \n&quot;);</FONT></TT>

</BLOCKQUOTE>

<HR>

<P>

Note that this program prints every line and prints only the first

word that does not contain a digit or a <TT><FONT FACE="Courier">.</FONT></TT>

character.

<H3><A NAME="UsingtheFOption">Using the <TT><FONT SIZE=4 FACE="Courier">-F</FONT></TT><FONT SIZE=4>

Option</FONT></A></H3>

<P>

The <TT><FONT FACE="Courier">-F</FONT></TT> option is designed

to be used along with the <TT><FONT FACE="Courier">-a</FONT></TT>

option. It is used to specify the pattern to use when splitting

input lines into words. For example, if the input fields on each

line that is input to a program are separated by a colon, you

would use the following statement: 

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -a -n -F: textfile</FONT></TT>

</BLOCKQUOTE>

<P>

In this case, the words in the input file are assumed to be separated

by a colon. You can use opening and closing slashes as pattern

delimiters. This means that both the following programs do the

same thing:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">prog -a -n -F: *.txt<BR>

<BR>

prog -a -n -F/:/ *.txt</FONT></TT>

</BLOCKQUOTE>

<H3><A NAME="Usingthe0Option">Using the <TT><FONT SIZE=4 FACE="Courier">-0</FONT></TT><FONT SIZE=4>

Option</FONT></A></H3>

<P>

The default end-of-input for one line of text in Perl is the newline.

That is, the Perl interpreter reads a line from an input file

or from the keyboard until it sees a newline character. You can

specify an end-of-line input character other than the newline

character by using the <TT><FONT FACE="Courier">-0<I> OOO</I></FONT></TT>

option. The <TT><FONT FACE="Courier">0</FONT></TT> here is the

digit zero for the option, and the letter <TT><FONT FACE="Courier">O</FONT></TT>

is the octal number to replace the newline character. For example,

the following command:

<BLOCKQUOTE>

<TT><FONT FACE="Courier">perl -0 07 program *.bin</FONT></TT>

</BLOCKQUOTE>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -