question-- Bourne (and C) SHELL (expression evaluation)

David Elliott dce at mips.UUCP
Sun Aug 17 05:42:34 AEST 1986


In article <150 at humming.UUCP> arturo at humming.UUCP (Arturo Perez) writes:
>Here's something I've wanted to do for a while but I can't seem to find the
>way to do it.
>
>In the csh you can do something like
>
>ls foo
>if (! $status) then
>   echo "foo exists"
>endif
>
>The  key  thing  here  is  the  ability  to NOT the value of status. How is
>this similar thing done in Bourne shell.
>

Wrong. The key thing here is the ability to evaluate an expression. Though
not built in to most versions of sh, the 'test' command can be used for a
similar effect, as can 'expr', and you can always use 'case'.

Here are three ways:

1. The 'test' command (this also exists as '[' in many systems, so I'll use
   that here)

	ls foo
	if [ $? -eq 0 ]
	then
		echo "exists"
	fi

2. The 'expr' command (since this prints the boolean truth value, we throw
   the output away)

	ls foo
	if expr $? != 0 >/dev/null
	then
		echo "exists"
	fi

3. The 'case' statement

	ls foo
	case "$?" in
		0)
			echo "exists"
			;;
	esac

There are two problems with this:

	1. You have programmed-in knowledge that '0' is 'true' (this isn't
	   really so bad).
	2. If 'foo' doesn't exist, 'ls' may still exit with a 0. A quick look
	   at the 4.3BSD code proves me out.

What is really needed here is what Guy Harris suggested, which is:

	if [ -f foo ]
	then
		echo "exists"
	fi

except that '[ -f foo ]' only returns true if 'foo' is a regular file.

This brings up a couple of really strange (but valid) examples:

	case `echo foo*` in
		"foo" | "foo "*)
			echo "exists"
			;;
	esac


	# 'dummy' ensures proper 'for' syntax
	for i in foo* dummy
	{
		case "$i" in
			"foo")
				echo "exists"
				break
				;;
		esac
	}

(Excuse the prodigious use of quotes. I'm a "fanatic".)

			David Elliott
			{ucbvax,decvax,ihnp4}!decwrl!mips!dce



More information about the Comp.unix mailing list