
On Sun, Nov 29, 2009 at 06:41:22PM +0100, legajid wrote:
Hello, I'm writing a little word game that consists of the following : between a consonant and a vowel, insert "AV" so "fabien" becomes "fAVabAVien".
When i type : f "fabine", the result is ok ("fAVabAVinAVe") When i type : f "fabien", the result is fAVabAVie *** exception :prelude empty list
Here's my program
voyelles="aeiouy" consonnes="bcdfghjklmnpqrstvwxz"
est_voyelle x = x `elem` voyelles est_consonne x = x `elem` consonnes
--f []=[] ; unuseful - conflict with f a = a
-- detect a vowel following a consonant trait a b = est_consonne a && est_voyelle b
f (a:b) is never invoked (i wrote EP instead of AV to trace the problem). f(a:b:c) seems to always take precedence over the other patterns. I expect f(a:b:c) to treat words greater than or equal to 3 letters, f(a:b) the last two letters of the word (no third part) and f a the last letter.
This is not correct. The patern (a:b:c) matches words greater than or equal to TWO letters, not three. In the case of a two-letter word, c is the empty list. For example, the word "in" is ('i':'n':[]).
f (a:b:c) = case trait a b of True -> a : (" AV " ++ f (b:c)) False -> a : f (b:c) f (a:b) = case trait a (head b) of True -> a : (" EP " ++ f ( b) ) False -> a : f ( b) f a = a
The problem is with the call to 'head b' -- when f is called on a one-letter word, it matches the pattern (a:b) with b the empty list, and the call to 'head' crashes. You do not need to check the trait in this case at all. In fact, you do not need this entire case at all! Just the first case and the third should suffice. -Brent