Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I have to write a script for this program. choose a random letter within a-z. Ask the user to guess the letter, match it with the chosen letter. If matched, display "correct", else prompt if the guessed letter is above or below the chosen letter. Can someone demonstrate with examples of how I might do this in the shell?

share|improve this question

closed as too broad by Patrick, Matteo, jasonwryan, Anthon, Braiam May 26 '14 at 13:26

There are either too many possible answers, or good answers would be too long for this format. Please add details to narrow the answer set or to isolate an issue that can be answered in a few paragraphs.If this question can be reworded to fit the rules in the help center, please edit the question.

Shell-script means KSH? (BA)SH? (T)CSH? Builtins only? Standard BSD-userland? – yeti May 26 '14 at 6:25
stack overflow is likely a better place to ask this question. – spuder May 26 '14 at 6:26
@yeti anyone among sh or bash – user3331420 May 26 '14 at 6:34
Is this a homework problem? – mdpc May 26 '14 at 6:56
What have you tried so far? What are you having problems with? We're happy to answer specific questions, but what you're asking for is someone to write a script for you. We're not here to do your work for you. – Patrick May 26 '14 at 6:56


BASH is nice for this job because BASH can generate the alphabet easily by using {a..z} and BASH can input a single char without needing to hit ENTER

$ cat guesschar.bash 
c=$(echo {a..z} | tr -d ' ')
while read -n1 -p'guess the char: ' ; do
        if [[ $REPLY < $x ]] ; then echo too low...
        elif [[ $REPLY > $x ]] ; then echo too high...
        else break
echo $x ... 'hit!'
$ bash guesschar.bash 
guess the char: m
too high...
guess the char: f
too low...
guess the char: j
too low...
guess the char: k
k ... hit!
share|improve this answer
thanks a lot...i can use the same code in sh also r wat?? – user3331420 May 26 '14 at 8:48
No. In sh this will be a much longer program. Compare the documentation. I think sh will not have the range expression {a..z}, not the RANDOM variable and not reading single keystrokes via read -n1. – yeti May 26 '14 at 9:06
No, this wouldn't be a much longer program in plain shell - I'm pretty sure I could do this shorter in shell - but both programs would be ASCII locale specific. If you wanted to do this and handle any alphabet... well, that would be a much longer program. – mikeserv May 26 '14 at 11:46
rand=$(tr -dc '[:lower:]' </dev/urandom | 
    dd bs=1 count=1 status=none)
until [ "$in" = "$rand" ] && echo "correct" ; do
    in=$(stty raw 
    dd bs=1 count=1 status=none </dev/tty 
    stty sane )

I think the above does what you need.

share|improve this answer
May I suggest head -c 1 instead of dd... for handling ASCII char one by one?. Just a suggestion though, but it's a bit more readable – lgeorget May 26 '14 at 12:22
@igeorget - good suggestion, but I think just the echo handles that. And dd is portable - even if /dev/urandom probably isn't. – mikeserv May 26 '14 at 12:23
hmmm... tested replacing occurrences of dd bs=1 count=1 status=none by head -c1, I got exactly the same behaviour. Well, anyway, that's just a matter of style, nothing important :) – lgeorget May 26 '14 at 12:31
What behavior? You mean the characters stringing together? That's stty raw doing that - that's why I added the echo. – mikeserv May 26 '14 at 12:32
You get my +1 for usage of /dev/urandom : shell has many tools for read/write operations and there is a PRNG accessible through the filesystem so no need to generate the random bytes in the code – lgeorget May 26 '14 at 12:33

If you want a portable way, you can try:

perl -e 'print ("a".."z")[rand 26]'
share|improve this answer
There's no need for the map here; you could just do perl -e 'print(("a".."z")[rand 26])'. – Tom Fenech May 26 '14 at 11:20
@TomFenech: Thanks, updated my answer! – cuonglm May 26 '14 at 11:37

Not the answer you're looking for? Browse other questions tagged or ask your own question.