.TI CSHELL/EXPRESSIONS
Expressions:  Arithmetic, Logic Operations, and Decisions [DRAFT]


An expression is a group of words (numbers, strings, and
operators separated by spaces) which the C shell
replaces by a single number, called its value.
The act of replacing an expression by its value
is a kind of substitution called evaluation, and forms the
basis for all arithmetic, logic operations, and decisions.
Loosely speaking, the term "expression" applies to any construct
whatever in the C shell, but here it has a specific sense.

Expressions are only evaluated, hence useful,
in conjunction with four built-in commands:
.IP
.nf
\fBif (\fIexpression\fP) then
\fBwhile (\fIexpression\fP)
\fB@ \fIname\fP = (\fIexpression\fP)
exit (\fIexpression\fP)\fR
.fi
.LP
The if and while statements use the value of \fIexpression\fP
to determine whether to execute the next command or group of commands.
In particular, when the C shell produces a value of zero (false),
the next group of commands is not done; otherwise it is done.
The \fB@\fP command (yes, it is actually a command),
not to be confused with the "at" command or the old default
line-kill character, stores the value of \fIexpression\fP
in the variable \fIname\fP.
Except for providing the only way to store the results of an
arithmetic or logic computation, it is identical to the "set" command.
The exit command quits the current shell (e.g., in a script)
and sets the command completion status (which other programs
sometimes want to know) with the value of \fIexpression\fP.

The command forms above do not all require parentheses,
but including them always is probably a good practice.
Moreover, the words inside an expression generally require spaces
between each other.
These words ultimately consist of strings (such as filenames),
numbers (such as 3.1415), and operators (such as +, \-, <, and >).
Usually, however, you have entered some of the words as
references to variable values, and so the shell will provide
the actual values during variable substitution just prior
to evaluating the expression.

The C shell has two main kinds of expressions:  arithmetic and logic.
Of logic expressions it has three kinds:  boolean, file enquiry,
and command status enquiry.
Each category is described below.

Arithmetic Expressions

Here evaluation simply means doing the arithmetic indicated,
and the value that replaces the expression is just the result.
You may use any of the operators and precedences valid in the
C programming language (without tremendously reliable results),
and octal numbers must begin with a 0.
The only numbers recognized by the shell are integers.

In the following examples, suppose
we have issued "% set y = 8 ; set num = (4 168 10 8808)":

.nf
    EXPRESSION          VALUE           EXPRESSION              VALUE
    (2 + 2)             4               (5 - 27 + 7)            -15
    (3 + $y + $num[3])  21              ($num[4] - 5)           8803
    (5 * 5)             25              (24 / $y - 6)           -3

% @ x = (354 - 128 + 52 * 5 / 3)
% echo Result is $x
Result is 174
% set y = (354 - 128 + 52 / 3)
% echo Result is $y
Result is 354 - 128 + 52 / 3
.fi


Logic Expressions

Evaluation means asking the question "Is it true that \fIexpression\fP?",
where \fIexpression\fP is a statement or assertion phrased in C Shell terms.
The value replacing it is 1 if the statement is true, 0 if false.
There are three kinds of logic expressions:  boolean, file enquiry,
and command status enquiry.
Any nonzero valued expression is taken as true, whatever you
may have intended (e.g., (3 + 2) is both 5 and true).

Boolean Expressions

These expressions, named after the English mathematician George Boole,
make assertions about the relative sizes of two numbers.  There are
8 kinds of assertions,

.nf
    ==    literal equals             !=    literal not-equals
    =~    regular expr. equals       !~    regular expr. not equals
    >     greater than               <     less than
    >=    > or =                     <=    < or =,

2 ways to combine two assertions,

    &&    and                        ||    or

and one way to negate an assertion

    !     not

Here are some examples:

    EXPRESSION          VALUE           EXPRESSION           VALUE
    (3 > 2)             1               (-5 < $num[3])       1
    (234 <= 234)        1               (234 <= 233)         0
    (2 == $y || 3 > 2)  1               (1 > -8 && 3 > 1)    1
    (1)                 1               (2 + (5 == 5))       3
    (prog.c == *.c)     0               (prog.c =~ *.c)      1

% set x = 340
% if ($x > 200)   echo You cannot afford it.
You cannot afford it.
.fi

File Enquiry Expressions

These have the form (-L \fIfilename\fP), where the `L' specifies one of
8 different assertions about \fIfilename\fP.
You may employ these to have the shell determine whether or not
permission is granted for a certain file, whether it is a directory, etc.
The possible choices for `L' are:

.nf
        r       read access             o       ownership
        w       write access            z       zero size
        x       execute access          f       plain file
        e       existence               d       directory

Here are some examples.

% if (! -z /usr/spool/mail/jak)  echo You have mail.
You have mail.
% if (! -z netcopy.out)  echo ready
% if (! -e stuff)   echo Not executable
.fi

Command Status Expressions

These have the form ( { \fIcommand\fP } ), where the shell
executes \fIcommand\fP during evaluation, and uses the
completion status as the value of the variable.
Note the spaces between \fIcommand\fP and the {}'s.
Unlike command substitution, nothing special happens to
the output of \fIcommand\fP.
In fact, frequently you do not need output anyway since
the expression relies upon the return status.
In the examples below the \-s option
suppresses any printed output in both cases.

For instance, to take a certain action in case two files differ,

if ( { cmp -s file1 file2 } ) then ...

or to leave a script and let the calling process know
of a match for a string in a file,

exit ( { grep -s string file } )


jak
