YOUR FEEDBACK
More on the Software Assembly Question - Do Design Patterns Help?
Yanic wrote: Hi, > UML and MDA are being changed to be more data and doc...


2007 West
GOLD SPONSORS:
Active Endpoints
Your SOA Needs BPEL for Orchestration
BEA
Virtualized SOA: Adaptive Infrastructure for Demanding Applications
Nexaweb
Overcoming Bandwidth Challenges with Nexaweb
TIBCO
What is Service Virtualization?
SILVER SPONSORS:
WSO2
Using Web Services Technologies and FOSS Solutions
Click For 2007 East
Event Webcasts

2008 East
PLATINUM SPONSORS:
Appcelerator
Think Fast: Accelerate AJAX Development with Appcelerator
GOLD SPONSORS:
DreamFace Interactive
The Ultimate Framework for Creating Personalized Web 2.0 Mashups
ICEsoft
AJAX and Social Computing for the Enterprise
Kaazing
Enterprise Comet: Real–Time, Real–Time, or Real–Time Web 2.0?
Nexaweb
Now Playing: Desktop Apps in the Browser!
Sun
jMaki as an AJAX Mashup Framework
POWER PANELS:
The Business Value
of RIAs
What Lies Beyond AJAX?
KEYNOTES:
Douglas Crockford
Can We Fix the Web?
Anthony Franco
2008: The Year of the RIA
Click For 2007 Event Webcasts
SYS-CON.TV
TOP LINKS YOU MUST CLICK ON


String and Numeric Test Statements
Looping and flow control

Digg This!

Last month I talked about the file-related options to the test command and how that helps you create smart and sophisticated shell scripts. This time I want to look at the additional conditions available for looping and flow control.

String Tests

One common test in shell scripts is to ascertain whether something the user has typed in or something pulled out of a data stream or file matches a specific pattern or string. The first of these tests is -z $string, which returns true if the string is zero length, false otherwise. Consider this snippet:


empty=""

if [ -z $empty ] ; then
  echo the length of empty is zero
else
  echo the length of empty is non-zero
fi

You can easily experiment and verify that if you set the variable empty to anything at all, the test will be nonzero, and if you leave it blank (or don't have it as a defined variable at all, for that matter) it'll be considered zero.

Somewhat confusingly, string tests in the test program (that is, string tests for shell scripts overall) are done with the following four operators: =, !=, <, or >. If you want to test a variable to see if it's a certain value, here's how that would look:

if [ $yourvar = "quit" ] ; then

The concept of less than or greater than is worth a bit of explanation too: it's an ASCII comparison, so "cat" is less than "dog," but, since it's ASCII, it also means that "+++" is less than "aardvark" too. Logically, this test should then work:

if [ "+++" < "aardvark" ] ; then

In fact, that'll fail with an annoying error message "-bash: aardvark: No such file or directory." This is happening because the shell is parsing and interpreting the < as a file redirection symbol before it even hands the arguments to the test command. Annoying! To sidestep this, escape the angle bracket like this:

if [ "+++" \< "aardvark" ] ; then

To be honest, though, you won't see this very often. Much more common are the = or != notations.

To get input from the user, the shell has the read command. Here's an example of using read and a string test conditional:


echo -n "Your first name: "
read answer

if [ $answer = "Dave" ] ; then
  echo Hello Dave
else
  echo Too bad you are not Dave
fi

The one problem to be aware of with string tests is that if the variable isn't defined, doesn't have any value, or has a value that includes a space, you can end up with a syntax error. On the previous snippet, for example, entering "Super Guy" as the name produces:

test.sh: line 6: [: too many arguments

Fortunately you can sidestep this problem by making sure that you quote the variable reference. Use double quotes, though, because single quotes will prevent the variable from being expanded at all. Here's the fixed line:

if [ "$answer" = "Dave" ] ; then

Numeric Tests

The other type of test you might want to use is numeric, and this will be like a quick flashback to BASIC, if you've been around that long. The tests are -lt, -le, -eq, -ne, -gt, -ge, for less than, less than or equal, equal, not equal, greater than, or greater than or equal, respectively. Want to see if an input value is less than 10? Try this:

if [ "$input" -lt 10 ] ; then

What's unfortunate is that there isn't a simple built-in test for whether values match specific criteria (for example, integer only), but with some creative thought and a little subshell transformation trick, almost all tests can be easily done. To ensure that a value is an integer, here's how I'd approach the problem:


nonums="$(echo $answer | 
  sed 's/[0-9]//g')"
if [ ! -z "$nonums" ] ; then
  echo "Not an integer value."
  exit 0
fi

The basic idea is that we delete all digits in the string, then use the ! -z test (the "!" reverses the logic of the test) to see if the resultant string is zero or not. Put in the context of an actual - albeit simple - script, here's how this would look:


echo -n "Pick a number between 1 and 20: "
read answer

nonums="$(echo $answer | 
  sed 's/[0-9]//g')"
if [ ! -z "$nonums" ] ; then
  echo "Not an integer value."
  exit 0
fi

if [ $answer -lt 10 ] ; then
  echo "Your answer is less than ten"
else
  echo "Your answer is not less than ten"
fi

Let's wrap up here for now, and next month we'll look at more sophisticated loop control options, and perhaps begin building a numeric guessing game as a fun and interesting example script.

About Dave Taylor
Dave Taylor, a contributing editor to Linux.SYS-CON.com, has been involved with the Linux and Unix community since 1980 and has written a number of best-selling Unix books. Currently, he writes, teaches, and works as a management consultant to tech startups, along with his new venture, Ask Dave Taylor!, www.askdavetaylor.com and his personal blog is www.blog.Linux.SYS-CON.com. To contact Dave, please go to /www.intuitive.com/contact.shtml.

LATEST LINUX STORIES
Kevin Hoffman's Review of Iron Man
I took the advice of a friend of mine and steered clear of the 'normal' movie theaters and went a little out of the way to go to a DLP movie theater. The experience of comparing a regular movie theater to a DLP movie theater is like comparing standard def analog TV with a 1080i HDTV si
3rd International Virtualization Conference & Expo: Themes & Topics
From Application Virtualization to Xen, a round-up of the virtualization themes & topics being discussed in NYC June 23-24, 2008 by the world-class speaker faculty at the 3rd International Virtualization Conference & Expo being held by SYS-CON Events in The Roosevelt Hotel, in midtown
Verizon Becomes a Counter-Android Linux Convert
Verizon Wireless is snubbing Google's Linux-based Android initiative to go with the LiMo Foundation's mobile Linux spec for its next wave of mobile phones expected next year. Along with Verizon, Mozilla signed up - giving the consortium its first major open source ISV - and a key one f
Adaptec Launches New Series 2 RAID Controller For Linux Users
Adaptec unveiled a new family of entry-level Unified Serial RAID controllers. The new low-profile Series 2 RAID controllers, built on the same Adaptec dual core RAID-on-Chip (ROC) architecture used in its successful Series 5 RAID controllers, provide significant performance enhancement
JavaOne 2008: Sun Challenges Linux
Sun's mule train has finally pulled into Indiana after three years on the road. Indiana is the Linux-friendly Fedora-like OpenSolaris project meant to move the Solaris-shy Linux community off Linux and on to Solaris tempted by Solaris widgetry like the highly scalable, rollback-easy, 1
Curl Announces Support for Ubuntu for Enterprise RIA Platform
Curl announced it has released the availability of an Ubuntu Installer for the Curl Rich Internet Application (RIA) platform. Curl is a Rich Internet Application platform that competes with Adobe AIR/Flex, Silverlight, and Ajax. Curl has been shipping with Linux support for RedHat 9, S
SUBSCRIBE TO THE WORLD'S MOST POWERFUL NEWSLETTERS
SUBSCRIBE TO OUR RSS FEEDS & GET YOUR SYS-CON NEWS LIVE!
Click to Add our RSS Feeds to the Service of Your Choice:
Google Reader or Homepage Add to My Yahoo! Subscribe with Bloglines Subscribe in NewsGator Online
myFeedster Add to My AOL Subscribe in Rojo Add 'Hugg' to Newsburst from CNET News.com Kinja Digest View Additional SYS-CON Feeds
Publish Your Article! Please send it to editorial(at)sys-con.com!

Advertise on this site! Contact advertising(at)sys-con.com! 201 802-3021

SYS-CON FEATURED WHITEPAPERS

ADS BY GOOGLE