計算機科学のブログ

関数型プログラミングの基礎 - ファーストクラス関数 - 関数を返す関数、case式

入門Haskellプログラミング (Will Kurt(著)、株式会社クイープ(監修、翻訳)、翔泳社)の UNIT1(関数型プログラミングの基礎)、LESSON 4(ファーストクラス関数)、4.4(練習問題)、Q4-2の解答を求めてみる。

コード

sample.hs

main :: IO ()
main = do
  let name = ("Will", "Kurt")
  print $ addressLetter name "ny"
  print $ addressLetter name "sf"
  print $ addressLetter name "reno"
  print $ addressLetter name "dc"
  print $ addressLetter name "other"

addressLetter :: ([Char], [Char]) -> [Char] -> [Char]
addressLetter name location =
  let locationFunction = getLocationFunction location
   in locationFunction name

getLocationFunction :: String -> ([Char], [Char]) -> [Char]
getLocationFunction location = case location of
  "ny" -> nyOffice
  "sf" -> sfOffice
  "reno" -> renoOffice
  "dc" -> dcOffice
  _ -> (\name -> fst name ++ " " ++ snd name)

sfOffice :: ([Char], [Char]) -> [Char]
sfOffice name =
  let lastName = snd name
      nameText = fst name ++ " " ++ lastName
   in if lastName < "L"
        then nameText ++ " - PO Box 1234 - San Francisco, CA, 94111"
        else nameText ++ " - PO Box 1010 - San Francisco, CA, 94109"

nyOffice :: ([Char], [Char]) -> [Char]
nyOffice name = fst name ++ " " ++ snd name ++ ": PO Box 789 - New York, NY, 10013"

renoOffice :: (a, [Char]) -> [Char]
renoOffice name = snd name ++ " - PO Box 456 - Reno, NV 89523"

dcOffice :: ([Char], [Char]) -> [Char]
dcOffice name = fst name ++ " " ++ snd name ++ ", Esq. - PO Box ..."

入出力結果(Terminal, Zsh)

% runghc sample.hs
"Will Kurt: PO Box 789 - New York, NY, 10013"
"Will Kurt - PO Box 1234 - San Francisco, CA, 94111"
"Kurt - PO Box 456 - Reno, NV 89523"
"Will Kurt, Esq. - PO Box ..."
"Will Kurt"
%