Bourne tutorial



Yüklə 478,18 Kb.
Pdf görüntüsü
səhifə18/20
tarix08.10.2017
ölçüsü478,18 Kb.
#3721
1   ...   12   13   14   15   16   17   18   19   20

Expr - Bourne Shell Expression Evaluator

This section is on the expr command, used to perform expression evaluation.

The Bourne shell didn't originally have any mechanism to perform simple arithmetic. In older versions

of UNIX, it used external programs, either awk or the must simpler program expr. In UNIX System V,

and therefore in Solaris, expr was added to the Bourne shell, which increases the speed of any Bourne

shell script that uses the built-in version. If the full path-name is used, the external version is executed,

causing a slight speed penalty. There are four types of operations expr performs:

Arithmetic

Logical

Relational



String

Most of the operators are obvious:

     +-------------------------------------------------+

     |Operator

    Type      Meaning

       |


     +-------------------------------------------------+

     |


  +

 Arithmetic   Addition

       |

     |


  -

 Arithmetic   Subtraction

       |

     |


  *

 Arithmetic   Multiplication

       |

     |


  /

 Arithmetic   Division

       |

     |


  %

 Arithmetic   Remainder

       |

     +-------------------------------------------------+

     |

  =


 Relational   Equal to

       |


     |

>

 Relational   Greater Than



       |

     |


>=

 Relational   Greater Than or Equal to |

     |

<

 Relational   Less Than

       |

     |


<=

 Relational   Less than or Equal to    |

     |

 !=


 Relational   Not Equal to

       |


     +-------------------------------------------------+

     |


  |

  Boolean     Or

       |

     |


&

  Boolean     And

       |

     +-------------------------------------------------+

     |

  :


   String     Match or substitute      |

     +-------------------------------------------------+

Not so obvious is how to use these operators. The general form is

expression operator expression

First of all, there must be spaces between operators and expressions. The example below is incorrect:

expr 2+2


The proper form is

expr 2 + 2

which prints "4" to standard output. The second concern is the shell, which treats some of the

characters as meta characters. Therefore if you use any of these characters "*&|><()" you must place a

backslash before them, or put quotes around them. Examples:

Bourne Shell Tutorial

http://www.grymoire.com/Unix/Sh.html

52 of 66


11/21/2011 12:03 PM


# 2 times 10

expr 2 "*" 10

# or

expr 2 \* 10



# a complex expression

# true if both $a and $b are greater than zero

expr $a '>' 0 '&' $b '>' 0

# But this gives you an error if $a or $b are undefined

# so you should use

expr "$a" '>' 0 '&' "$b" '>' 0

The third potential problem is quoting too many characters. The expression

expr '2 + 2'

is not "4" but "2 + 2" which is five characters long. This allows strings with spaces to be compared:

expr $a = '2 + 2'

If only one expression is given, then expr simply echos it.

expr no


prints the word "no."

Another potential problem is variables that contain operators. The following example, which looks like it

might test if a variable is equal to an "=," generates an error:

A='='


# is $A an '='?

expr $A = '='

# WRONG - syntax error - same as 'expr = = ='

The fix is similar to the one used to fix test, i.e. add an extra character before the variable:

expr X$A = X=

Arithmetic Operators

Expr uses 32-bit, signed integers. Therefore negative numbers are acceptable. A common use is loops:

# count from 1 to 10

A=1

while [ $A -le 10 ]



do

echo $A


A=`expr $A + 1`

done


Relational Operators

Bourne Shell Tutorial

http://www.grymoire.com/Unix/Sh.html

53 of 66


11/21/2011 12:03 PM


The relational operators check to see if both expressions are integers. If so, the comparison is numeric. If one

or more expressions are non-numeric, the comparison is lexical. Therefore you can compare integers or

strings. The confusing part of the relational operators is deciding how to use the information. You see, the

operators output to standard output, and also return an exit status. Remember how the value of true is

typically non-zero, but a true exit status is zero? Well, expr continues this tradition. Consider the following

test:


expr 1 = 1

This outputs "1," or "true" to standard output, but returns an exit status of zero. To be precise, if the

expression has a value that is not equal to zero, and not equal to a null string, then the exit status is zero. An

exit status of one is the opposite, i,e, the output is a null string or zero. Expr will return an exit status of 2 if an

error occurs. The exit status can be used in simple tests:

expr $A = 1 > /dev/null && echo A = 1

Notice how the standard output had to be discarded, otherwise the script would print out a "1." The

expression can also be used in a loop:

A=1;

while expr $A '<=' 10 >/dev/null



do

A=`expr $A + 1`

echo $A

done


Relational operators always print a zero or one.

Boolean Operators

The two boolean operators operate on strings and integers. A null string and a zero are false. Anything else is

true. I mentioned the status before. This is a "side-effect," because the program also sends a string to standard

output. In other words, the designers of the expr program tried to make it as versatile as possible. Consider

the following:

expr $a & $b

If either variable is an empty string, or zero, the program prints zero. (The status is one.) If not, the program

exits with a status of zero, but it does not print a one. instead, it prints the value of variable "a." Imagine

Garry Owens or Don Pardo saying

Not only does expr return a status, but it prints too! And it doesn't just print zero or one. It prints

either zero, or the actual value of the expression, saving you time and money.

On the other hand, they may have simply felt printing a one would throw away information for no reason. The

"|" operator also returns zero if both expressions are zero or a null string. Otherwise, it returns either the first

expression, or the second. More precisely, expr looks at the first expression, and if not a zero or null, it

returns the value, otherwise it returns the second expression, not even checking its value. This is a little

confusion. A table might help. The first column is the expression. The second is the printout. The third column

is the exit status:

Bourne Shell Tutorial

http://www.grymoire.com/Unix/Sh.html

54 of 66

11/21/2011 12:03 PM




Yüklə 478,18 Kb.

Dostları ilə paylaş:
1   ...   12   13   14   15   16   17   18   19   20




Verilənlər bazası müəlliflik hüququ ilə müdafiə olunur ©genderi.org 2024
rəhbərliyinə müraciət

    Ana səhifə