change of conditions in recursive function - haskell

First of all this is an assignment so I don't want a complete solution :)
I'm going to calculate the value of a deck in the Cardgame blackjack.
Rules are all Aces are 1 or 11.
suppose my hand is: (Ace, 5), My hand is now 16. Next card is a 6, my hand is now (Ace, 5,6) 22 but the ace that I already calculated before must now change to one so my hand is at 12.
my Hand datatype is defined recursive by
data Hand = Empty | Add Card Empty
so calculate a hand with fixed values are done by
valueOfHand (Add c h) = cardValue c + valueOfHand h
What's the pattern to change the values that appeared before?

I'm not sure if your class has already covered the list monad, but I think that's the most natural way to solve this. So instead of having cardValue return a simple value, it should return a non-deterministic value that lists all the possible values that the card might have, i.e.
cardValue :: Card -> [Int]
cardValue Ace = [1, 11]
cardValue Two = [2]
...
valueOfHand will then have two parts: one that computes a list of all possible hand values and another that selects the best, legal hand.
Let me know if this is enough for you to solve it or if you need more hints.

If, as you indicate in the comments, Aces may only have one value per hand (so a hand of three Aces is 3 or 33), then it makes sense to define your valueOfHand :: Hand -> Integer function in a way that first totals up non-Ace cards and then handles the Aces.
I would expect such a function would be based around something like this:
valueOfHand Empty = 0
valueOfHand h = valueOfAces (filter (\c -> c == Ace) h) (filter (\c -> c /= Ace) h)
For some function valueOfAces :: Hand -> Hand -> Integer.

Related

Haskell - dealing with recursive functions that branch out

So I am rather new to Haskell and I am having a lot of a trouble not thinking imperatively. And I need to create a recursive function that branches out. Let me explain what I mean.
My function takes some tuple and 3 integers (a, b, c). If some conditions are met, the function should stop. Otherwise, the function calculates the new values of (a, b, c), calculates a list based on the elements of the tuple, and call itself for each element of the list.
For now, the function looks something like this (I have omitted the elements of the tuple since it doesn't matter):
function :: () -> Int -> Int -> Int -> [(Int, Int, Int)]
function someTuple a0 b0 c0
| someCondition = [(a0, b0, d0)]
| otherwise = [function () a1 b1 c1 | x <- someList]
where a1 = ...
b1 = ...
c1 = ...
someList = ...
The problem (as you can probably tell) is, that the function only returns the numbers computed on one branch of the recursion.
Now, the only thing I REALLY need are the 3 new numbers that are computed each time the function is called. I an ideal world (or in an imperative language), I could use some gimmick like appending the numbers to a global list each time the function is called. This however, is not really a solution in Haskell.
I hope I managed to explain the problem in an understandable manner. I would really appreciate it if somebody could guide me in the right path. So in short, what I need to know is how I can get the new values of (a, b, c) that are computed EACH time the function is called.
Recursive functions that "branch out" are commonplace in implementing "divide and conquer" algorithms (e.g. Quicksort). Your problem is that you divide allright, but the conquer step is missing:
| otherwise = [function () a1 b1 c1 | x <- someList]
Here you subdivide the problem into a number of subproblems (enumerated by someList, and then just return the list of results. Alas, that won't even typecheck: you need to return a result (a list), not a list of results (i.e. a list of lists).
How to combine the results depends on your problem, you need a function with type [result] -> result (where result = [(Int,Int,Int)] in your specific case). concat is such a function, head is another (which would indeed make your function only return the numbers computed on one branch of the recursion, like you say it does)

Haskell function reverse engineering

I need to analyze the following Haskell function, which is part of a bigger program (extracted from here):
findMoves :: Position -> [Position]
findMoves (left,right) = elems $ Data.Set.filter validPos moves where
moves | Farmer `member` left = Data.Set.map (move delItem addItem) left
| otherwise = Data.Set.map (move addItem delItem) right
move f1 f2 item = (f1 item left, f2 item right)
delItem item = delete Farmer . delete item
addItem item = insert Farmer . insert item
I understand everything until the end of the where statement, but I haven't seen anything like the move f1 f2 item declaration before, I'm starting right now with Haskell. What is that? Something like an in-line function declaration? I just need to know which kind of statement is that, I'm not asking you to explain what the developer was trying to do (that's my task).
Thanks
Maybe take a look at some easier example and see if we can figure out what's going on
foo :: Int -> (Int, Int)
foo x = apply add sub x
where
apply f1 f2 someThing = (f1 x someThing, f2 x someThing)
add k = (+) (1) --<---------------^
sub s = (-) (10) -- <-----------------------------^
With the input 5, this would give output (6,5). It can often be useful to say something like "i want to apply x to some function", where this function itself takes other functions as input. So we can make it more general by saying: here is a function, that together with 2 other functions, gives me my desired output.
In the short example above we say, "here is a function, that together with two other functions, applies those functions with some values to make a pair". And we dont really care what those functions are, in this case we used the functions add and sub, but that doesnt have to be the case.

Check and see if all elements of a list match a parameter

I want to make a function that checks to see if each row of the board for the Bert Bos puzzle is red one row at a time, but conceptually I'm having a hard time with this. Initially I make the board with all blue squares, but once the squares have been flipped with a flip function, the allRed function should be able to tell if the row is all red or not. Each row is represented by a list of colors, either Blue or Red
I know I should be using the all function, but I'm having some problems actually writing it out for my situation
Here is what I have so far:
generateboard :: Int -> [[Color]]
generateboard n = replicate n (replicate n Blue)
allRed :: [[Color]] -> Bool
let board = generateboard
allRed board = []
allRed board = all ([x:_ | x <- board, x == Red])
allRed board
There are many mistakes and misunderstandings here. I recommend reading any of the introductory Haskell materials to strengthen your basic understanding of the language. I will answer the question directly nonetheless.
generateboard looks great.
You are right to think all :: Foldable t => (a -> Bool) -> t a -> Bool will help us define allRed. If the type is confusing you can instead think of it as (a -> Bool) -> [a] -> Bool. The documentation says:
Determines whether all elements of the [list] satisfy the predicate.
To use all we need a predicate (a function) with type a -> Bool and a list of type [a]. We know what the predicate needs to be:
\x -> x == Red
Another way to write this is:
(==) Red
The predicate has type Color -> Bool and so our list must then have type [Color]. However, we have a list of type [[Color]]. There are two ways I can see to go about this.
The simpler idea is to observe that the board structure is irrelevant if all we care about is the cells. Therefore, we can flatten the structure with concat :: [[a]] -> [a]. Then our solution is thus:
allRed xs = all ((==) Red) (concat xs)
Which is also written:
allRed = all ((==) Red) . concat
Another solution is to observe that if all rows are red then the whole board must be red. This solution is:
allRed xs = all (all ((==) Red)) xs
Which is also written:
allRed = all (all ((==) Red))
First, the all function:
all :: (a -> Bool) -> [a] -> Bool
all p xs = ...
takes a function p representing a property and a list xs and tests if p x is true (i.e., if x has property p) for every element x of xs. (For example, all even [2,4,7] checks if all elements of the given list are even, and it returns False because even 7 equals False.) So, to use all, you need two arguments -- a list of items to check, and a function that checks one item.
Second, when faced with the problem of processing a data structure in Haskell (in this case [[Color]]), an excellent rule of thumb is to the deconstruct the structure from the outside in, using one function for each level of structure. You have an (outer) list of (inner) lists of colors, so start with the outer list, the list of rows.
How would you write a function that checks if all the rows in the outer list satisfy the property that they "contain only red colors"? Or, to put it more simply, how would you write this function using all if you already had a helper function redRow that expressed the property of a row having only red colors?
redRow :: [Color] -> Bool
redRow row = ...
If you can write allRed board using all, board, and redRow, you'll have reduced the problem to writing the definition of redRow, which operates on a simpler data structure, an (inner) list of colors.
To write redRow, you should likewise be able to use all again with a function expressing the property of a color being red:
isRed :: Color -> Bool
isRed col = ...
(or using an equivalent lambda or "section" directly).
In this case, another approach is possible, too -- you could use concat to "flatten" the outer and inner list together and then tackle the easier problem of checking if all colors in a big long list are red.

How to go up on a tree in haskell?

Maybe the question is not suiting the topic i am going to approach
But i will try to explain the best i can:
I have a genealogical tree that has this structure:
data GT = Person Name Father Mother
| unknown
type Father = GT
type Mother = GT
type Name = String
I need to find out the grandfathers of a given name:
grandfathers :: Name -> GT -> [Name]
this is the best i could do:
grandfathers :: Name -> GT -> [Name]
grandfathers s (Person x f m) = if (searchgrandson s f 0) then [x] else (grandfathers s f)
where
searchgrandson s unknown k = False
searchgrandson s (Person x f m) k = if s==x && k<2 then True
else searchgrandson s f (k+1)
of course that for this tree it works, because my code goes all the way through the left side, ignoring the mother side, and giving only the grandfather, and not the grandmother right?
$grandfathers "grandson" (Person "grandpa" (Person "son" (Person "grandson" unknown unknown ) unknown ) unknown )
["grandpa"]
EDIT:
after following the dfeuer advice:
avos_ :: Nome -> AG -> Int
avos_ s Desconhecida = 0
avos_ s l#(Pessoa x p m) = encontraneto s l 0
where
encontraneto s Desconhecida k = 0
encontraneto s (Pessoa x p m) k = if s==x then k
else encontraneto s p (k+1) + encontraneto s m (k+1)
This gives me the depth of the tree where the grandson is, searching both sides. After this would be simple...
Thanks!
A good way to go about solving this problem is to decompose it into two functions. One of the functions will search the tree for zero or more matches against a name and return zero or more trees, starting from the place where the match occurred; the root of each tree will be the person that matches the name. The other function will simply take a tree and return zero, one, two, three or four names corresponding to the grandparents of the person at the root of the tree.
The types of the first function is easy:
searchPerson :: Name -> GT -> [GT]
The type of the second function is also straightforward
getGrandparents :: GT -> [Name]
Now, since the first function returns a list of GT, rather than a single GT, the second function should be mapped over the results of the first function (or, said other way, lifted to operate on lists of GT):
map getGrandparents (searchPerson x myGenTree)
Writing the second function (getGrandParents) is trivial and can be achieved with pattern matching, deconstructing the GT type up to the second level of nesting, but you would probably like to save yourself some typing and create a helper function to operate on each parent and return their parents.
The first function (searchPerson) is also trivial, and can be done in a couple of ways. One way is to simply use recursion looking for a match on a name and returning a list of all the subtrees that had a match. The other option is to simply return a list of every possible subtree in that tree, starting from any possible offset, and to use a filter to only keep those subtrees whose root is a match. The second option is more "wholesome" and equivalent to addressing a similar problem in lists (the function that returns all sublists is tails) so would probably appeal to some people more. You may think that the second approach is wasteful, but Haskell immutability and lazyness should make it pretty efficient too.
I quickly put together the code in my fpcomplete account and will gladly post the URL in a comment below if you ask, but I don't want to spoil the fun of coming up with the solution on your own.

Haskell division algorithm function

my professor assigned me a pretty basic lab that is mostly done. Essentially what it should do resembles divMod. It should output the quotient and the remainder using a recursive function. Below is the code. I am not quite sure what is going on syntax wise also if someone could maybe explain what might go in the "Fill this in" part. I understand that a < b is the simple case meaning the quotient is zero and the remainder is a. So q = 0 and r = a. This will eventually be achieved by repeatedly subtracting b from a. Let 17 be a and 5 be b, so as follows: 17-5=12 then 12-5=7 then 7-5=2 which means the quotient is 3 and remainder is 2. So I understand whats going on I just cannot write it in haskell. Thanks for any help. Sorry for the super lengthy question.
divalg :: Int -> Int -> (Int, Int)
divalg a b | a < b = --Fill this in--
| otherwise = let (q, r) = divalg (a - b) b
in --Fill this in--
From the type signature, you can see that divalg takes two Ints and returns a pair of Ints, which you correctly identified as the quotient and remainder. Thus in the base case (where a < b), you should do that: return a tuple containing the quotient and remainder.
In the recursive case, the recursive call is already written. When thinking about recursion, assume the recursive call "does the right thing". In this case, the "right thing" is to return the quotient and remainder of (a-b)/b. I'll leave the math to you, but the basic idea is that you need to modify the tuple (q,r) to get a new tuple containing the quotient/remainder for a/b. How do I know this is the right thing to do? Because the type signature told me so.
In short, your code will look something like this:
| a < b = (___, ___)
| otherwise = let ...
in (___, ___)

Resources