I am having trouble with how to use isUpper, isLower, and isDigit. Specifically I am trying to take a string and return a list of tuples for each character in the string containing three Bool values for if the character is an uppercase letter, a lowercase letter, or a digit. So the string "Ab2" would return the list [(True, False, False), (False, True, False), (False, False, True)]. This is what I have:
import Data.Char
uppercaseList :: [a] -> [(Bool, Bool, Bool)]
uppercaseList xs = [(isUpper, isLower, isDigit)]
I think I need to pass the character of the string into isUpper, isLower, and isDigit, but I don't see how to. I'm sorry if this is a dumb question, but nothing I've found addresses my confusion so far.
The functions isupper() and islower() in C++ are inbuilt functions present in “ctype. h” header file. It checks whether the given character or string is in uppercase or lowercase.
Python String isupper() is a built-in function that returns “True” if all the characters in the string are uppercase. The String islower() is a built-in function that returns “True” if all the characters in the string are lowercase. These are the built-in method used for string handling.
The isupper() & islower() return boolean values whereas the upper() & lower() function returns strings either in uppercase or lowercase.
You need to do check on each element of the list (xs
). Usually this kind of task is done by using map
import Data.Char
uppercaseList :: String -> [(Bool, Bool, Bool)]
uppercaseList xs = map (\x -> (isUpper x, isLower x, isDigit x)) xs
or list comprehension
uppercaseList xs = [ (isUpper x, isLower x, isDigit x) | x <- xs ]
or write from scratch
uppercaseList [] = []
uppercaseList (x:xs) = (isUpper x, isLower x, isDigit x) : uppercaseList xs
The problem with your approach:
uppercaseList xs = [(isUpper, isLower, isDigit)]
is that it does not take the list xs
into account at all: it is not mentioned in the body. So that means xs
has no impact on the output.
What you have done ihere is constructing a list as output with one element: a tuple that contains three functions (yes these are functions, not Bool
s).
In order to inspect the character, you need to call the functions on an element of the list.
Calling a function on a list is done with map :: (a -> b) -> [a] -> [b]
. Map takes as first argument a function f
, and as second argument a list of elements (for instance [x1, x2, x3, x4]
). It applies the function f
on all elements of the input, and generates a list [f x1, f x2, f x3, f x4]
). This is done in a lazy manner.
Here we thus need a function f :: Char -> (Bool, Bool, Bool)
. Based on the specifications, the function looks like:
import Data.Char(isUpper, isLower, isDigit)
f :: Char -> (Bool, Bool, Bool)
f x = (isUpper x, isLower x, isDigit x)
We can then write:
uppercaseList :: [Char] -> [(Bool, Bool, Bool)]
uppercaseList = map f
Since it is weird to see a function f
(we can of course give it a more semantical name), at the top level of a file. We can decide to scope it (or use a lambda expression instead):
uppercaseList :: [Char] -> [(Bool, Bool, Bool)]
uppercaseList = map f
where f x = (isUpper x, isLower x, isDigit x)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With