Stable Exchange Stable Exchange – Haskell Stable Exchange

I've set up a stable marriage problem at Haskell a few months ago. It is not optimized at all and I would like to know how to improve it from the point of view of performance and readability.

data Sex = Male | Derived Woman (Eq, Show)
data Virtue = Intelligence | Appearance | Drifting Kindness (Eq, Show, Enum)

data Parameter = Parameter {
virtue :: virtue,
value :: Int
} drifting (Eq, Show)

data Person = Person {
name :: String,
sex :: sex,
preferences :: [Virtue],
settings :: [Parameter],
partner :: maybe nobody
} drifting (Eq, Show)

List of results of women sorted by preferences of a man by defaultRateFunction :: Person -> Person -> Int. In my implementation, it depends on the judges The preferences and rated person settings. I will not put it there for brevity. You can find the full program in a link to Gist at the bottom of the article. Imagine that this function is all you want.

personalRating :: Person -> [Person] -> [Person]
personalRating x ys = sortBy (comparison ( y -> defaultRateFunction x y)) ys

The man makes an engagement proposal for the woman and if she has no partner, she responds positively (True) and if it does, if the notation of the new partner> in relation to the old – "returns" True and if that is not the case – False

proposal :: Person -> Person -> Bool
woman man proposal
| isNothing (female partner) = True
| defaultRateFunction male> defaultRateFunction female (from $ partner wife) = True
| otherwise = false

The man makes a proposal for each woman in a woman until he finds one that will respond positively. Assumed that there is at least one of this type in the table

findTheBride :: Person -> [Person] -> Person
find male women
| male proposal (female head) == True = female head
| otherwise = findTheBride male (female tail)

The ugliest part is algorhitm marrige himself. As I call her recursively, I have to clean every time she finds a partner and check if a woman has an ex-partner, and handle their "breakup" as well.

marrige :: [Person] -> [Person] -> [Person]
young men
| sm == [] = women
| nothing is ex = marrige
(fsmWithNewPartner: (removes men fsm))
(fsmPartnerWithFsm: (removes females fsmPartner))
| if not = marrige
(fsmWithNewPartner: (fromJust ex) {partner = Nothing} :( delete fsm $ delete (fromJust ex) males))
(fsmPartnerWithFsm: (removes females fsmPartner))
sm = filter ( x -> partner x == nothing) men - single men
fsm = head sm - Single fist
fsmPartner = findTheBride fsm (FSF Women's Personal Ranking) - Fist partner of a single man
ex = partner fsmPartner - Ex of partner (maybe)
fsmWithNewPartner = fsm {partner = Just fsmPartner}
fsmPartnerWithFsm = fsmPartner {partner = Just fsm}

Full version of the program (where random person data is generated) available on Gist.