web developer & system programmer

coder . cl

ramblings and thoughts on programming...


small programming exercise

published on 10-02-2012 / updated: 10-02-2012
posted in: development, haskell, programming, tips
by Daniel Molina Wegener

On a programming forum I have found a small programming problem about guessing numbers. I have implemented its solutions this morning using Haskell, only to practice a little some Haskell programming. The problem is quite easy to solve. I have used lists instead of arithmetic operations to reach the final number without errors, avoiding user mistakes.

we all know the classic «guessing game» with higher or lower prompts. lets do a role reversal; you create a program that will guess numbers between 1-100, and respond appropriately based on whether users say that the number is too high or too low. Try to make a program that can guess your number based on user input and great code!

And here is my solution — where it has some validations to avoid the wrong input.


module Main where

import System.IO.Unsafe
import Text.Printf

promptOptions :: String
promptOptions = "[Yes (y), Higher (h), Lower (l)]"

queryNumber :: Int -> String
queryNumber n = printf "Is your number %s? %s"
                       ( show n ) promptOptions

printNumber :: Int -> String
printNumber n = printf "Your number is %s"
                       ( show n )

promptNumber :: Int -> IO String
promptNumber n = putStrLn ( queryNumber n ) >> getLine

reduceList :: String -> Int -> [Int] -> [Int]
reduceList m n xs | m == "h" = filter (> n) xs
                  | m == "l" = filter (< n) xs
                  | m == "y" = [n]
                  | otherwise = xs

searchNumber :: [Int] -> IO ()
searchNumber m = let ln = length m `div` 2
                     nm = m !! ln
                     mn = unsafePerformIO $ promptNumber nm
                     rs = reduceList mn nm m
                     in case length rs of
                             1 -> putStrLn $ printNumber $ head rs
                             _ -> searchNumber rs

main :: IO ()
main = do putStrLn "Is your number odd (o) or even (e)?"
          x <- getLine
          case x of
               "e" -> searchNumber $ filter odd [ 1 .. 100 ]
               "o" -> searchNumber $ filter even [ 1 .. 100 ]
               _   -> main

To compile this program with GHC, try ghc --make prog.hs -o prog, also it works with runghc prog.hs.


one comment to “small programming exercise”

  1. Solution in C#:

    
    using System;
    
    namespace GuessingNumber
    {
    	class MainClass
    	{
    		public static void Main (string[] args)
    		{
    			var min = 1;
    			var max = 100;
    			while (min != max)
    			{
    				var myguess = (max + min) / 2;
    				Console.WriteLine (
    					"nIs your number {0}? Yes (y){1}{2}",
    					myguess,
    					(myguess  min) ? ", Lower (l)" : string.Empty);
    				var response = Console.Read ();
    				if (response == (int) 'y')
    				{
    					Console.WriteLine ("nDone!");
    					return;
    				}
    				if (myguess  min && response == (int) 'l')
    					max = Math.Max (myguess - 1, min);
    			}
    
    			Console.WriteLine ("nYour number is {0}", min);
    		}
    	}
    }
    

post a comment

XHTML: You can use these tags: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>