Haskell

let式。

特定の定義のみで有効な束縛ができる。 main = print $ letTest1 5 letTest1 n = let x = n + 1 y = n + 2 z = n + 3 in x * y * z where節と似ているけど、以下の2点が違う。 letは式なのでlet自体にも値を持つ、whereは節なので値を持たない whereは複数の…

関数名、変数名。

関数名、変数名に使える文字は以下の通り。 アルファベット 数字 _(アンダースコア) '(シングルクォート) 1文字目はアルファベットの小文字か_でないといけないが、Haskellの仕様書では_を避けるとあるとのこと。 また'は補助的な関数の名前によく使われる。…

演算子を独自に定義。

main = do print $ (+*) 2 3 print $ 2 +* 3 (+*) :: Int -> Int -> Int (+*) x y = (x + y) + (x * y) 結果。 11 11

case式。

関数定義じゃなくても、パターンマッチ、ガードが使える。 main = putStr $ case "abc" of "" -> "" all@(c:cs) | all == "abc" -> "ABC" | otherwise -> all 結果。 ABC それにしても、何と意味のないサンプルだろうか。

ガード。

main = do print $ guardTest 1 print $ guardTest (-1) guardTest :: Int -> Int guardTest x | x < 0 = 0 | otherwise = x 結果。 1 0 から=までガード(guard) ガードはパターンマッチと同様に仮引数の値によって複数の関数を定義できる。 パターンマッチ…

@パターン(アズパターン)

as-pattern。 main = asTest [1, 2, 3] asTest all@(n:ns) = do {print $ all; print $ n; print $ ns} 結果。 [1,2,3] 1 [2,3] nが1、nsが[2,3]に、allは[1,2,3]、つまりリスト全体に束縛される。

インデントを使わずに書く。

main = do cs <- getContents putStr cs は main = do {cs <- getContents; putStr cs} このようにブロックを{}で囲み、式を;で区切って書くことができる。

パターンマッチいろいろ。

変数パターン _パターン(アンダーバー) リテラルパターン タプルパターン データコンストラクタパターン n + kパターン いろいろある。 この中でよくわからないのが_パターン、データコンストラクタパターン、n + kパターン。 n + kパターンは使用頻度が低く…

リスト内包表記。

リスト内包表記(list comprehension) リストの中にそのリストの要素を生成する処理を書くような感じと理解。 [abs x | x <- [-1, -2, -3]] 結果。 [1, 2, 3] xにリストの要素が渡され、xに対してabs関数を適用、その結果がリストの要素となる。 リスト内包表…

null関数。

null :: [a] -> Bool 第1引数が空リストならTrueを返す。 null [] null "" null [1] 結果。 True True False

(++)関数。

(++) :: [a] -> [a] -> [a] リストを連結する。 [1] ++ [2,3] "a" ++ "bc" 結果。 [1,2,3] "abc"

タプルを処理する関数。

fst関数 fst :: (a, b) -> a 2要素のタプルの第1要素を返す。 fst (1,2) 結果。 1 2つ以上の要素を持つタプルに適用するとエラー。 名前の由来はfirst。 snd関数 snd :: (a, b) -> b 2要素のタプルの第2要素を返す。 fst (1,2) 結果。 2 名前の由来はsecond…

文字変換関数。

関数 機能 toLower 大文字→小文字 toUpper 小文字→大文字 ord 文字→文字コード chr 文字コード→文字 toLower、toUpper関数は引数に処理対象以外の文字が渡された場合、引数をそのまま返す。 Char.toLower 'a' Char.toLower '1' 結果。 'a' '1'

文字をチェックする関数。

Charモジュールに定義されているので、使用の際は、 import Char する。 関数 機能 isAlpha UnicodeのアルファベットならTrue isLower Unicodeのアルファベットで小文字ならTrue isUpper Unicodeのアルファベットで大文字ならTrue isAlphaNum Unicodeのアル…

数値変換。

整数型を他の型に変換 使用例 内容 toInteger x Int型の値xをInteger型に変換 fromInteger x Integer型の値xを数値型に変換(返り値の型は文脈で決定) fromIntegral x Int型またはInteger型の値xを数値型に変換(返り値の型は文脈で決定) 浮動小数点型を整数型…

Bool型の代表的な関数。

not関数 第1引数がTrueならFalse、FalseならTrueを返す。 not :: Bool -> Bool (&&)関数 第1引数、第2引数ともにTrueならTrueを返す。 (&&) :: Bool -> Bool -> Bool (||)関数 第1引数、第2引数のどちらがTrueならTrueを返す。 (||) :: Bool -> Bool -> Bool

数値の演算。

例 内容 x + y xとyの和 x - y xとyの差 x * y xとyの積 x / y xとyの商(浮動小数点同士のみ) x `div` y xとyの整除整除(整数同士のみ、負の無限大に向かってまるめる) x `quot` y xとyの整除整除(整数同士のみ、0に向かってまるめる) x `mod` y (x `div` y)…

型。

Bool型 TrueとFalse 整数型 Int型とInteger型がある Int型は基本的に32ビットの符号付き整数値、処理系によっては違うこともある Integer型は表現範囲に制限のない整数値 浮動小数点型 Float型とDouble型がある Float型は単精度の浮動小数点 Double型は倍精…

遅延評価。

評価しなければならない値が存在するとき、実際の計算を値が必要になるまで行わないことをいう。 必要な式だけ評価する main = do myIf (True) (putStrLn "then") (putStrLn "else") myIf :: Bool -> a -> a -> a myIf True t e = t myIf False t e = e 結果…

isPrefixOf関数

(Eq a) => [a] -> [b] -> Bool [a]の全要素が[b]の先頭からの要素に含まれていたらTrueを返す。 (Eq a) => import List main = do print $ isPrefixOf [1,2] [1,2,3] print $ [1,2] `isPrefixOf` [1,2,3] print $ [2,3] `isPrefixOf` [1,2,3] 結果。 True Tr…

tails関数

[a] -> [[a]] [a]内の全ての要素、第2以降の要素、第3以降の要素、以降、空リストまでをリストにして返す。 import List main = print $ tails [1, 2, 3] 結果。 [[1,2,3],[2,3],[3],[]]

any関数。

(a -> Bool) -> [a] -> Bool [a]の要素に対して(a -> Bool)を適用し、1つでもTrueの場合、Trueを返す。 main = do print $ any anyTest [2, 3, 4, 5, 1] print $ any anyTest [1, 2, 1] print $ any anyTest [2, 4, 5] anyTest :: Int -> Bool anyTest n = i…

コマンドライン引数を読み込む。

import System main = do args <- getArgs print $ args コンパイルし、コマンドライン引数に『a b c』と渡して実行。 結果。 ["a","b","c"] スペースで区切られた配列として返されているようだ。

import宣言。

様々な関数、変数が定義されているモジュールを使用する場合、import宣言を使用するとそのモジュールが使用可能となる。 import System 名前空間みたいなものか。 全ての関数、変数はいずれかのモジュールに属しており、モジュールを定義していない場合、そ…

where節。

where節以降で関数を定義すると、その直前で定義した関数からのみ使える関数が定義関数を定義、変数を束縛できる。 main = do print $ whereTest 1 whereTest :: Int -> Int whereTest n = plus 5 where plus :: Int -> Int plus num = n + num この場合、pl…

haskell-modeのインデント。

main = do cs -> getContents■ この状態でreturnキーを押すと main = do cs -> getContents ■ カーソルは先頭に来る。 Tabを押すと main = do cs -> getContents ■ getContentsのところに移動。 その後、ちまちまとcsのところに移動させていたけど、もう一度…

head関数。

リストの先頭の要素を返す。 head [1, 2, 3] head "abc" 結果。 1 'a' 空リストに適用するとエラー発生。 Exception: Prelude.head: empty list

tail関数。

リストの先頭以降の要素を返す。 tail [1, 2, 3] tail "abc" tail [1] 結果。 [2, 3] "bc" [] tail [1] の結果が [] となるのは、リストの末尾には常に空リストという特別な要素があるため。

filter関数。

filter :: (a -> Bool) -> [a] -> [a] 第2引数[a]の要素で(a -> Bool)がTrueの要素のみ集めてリストで返す。 main = print $ filter filterTest ["abc", "de", "f", "gh"] filterTest :: String -> Bool filterTest cs = if length cs == 2 then True else F…

map関数の動作。

main = print $ map square [1, 2, 3] square :: Int -> Int square n = n * n 結果。 [1,4,9] map関数の定義はこんな感じ。 map :: (a -> b) -> [a] -> [b] map f [] = [] map f (x:xs) = f x : map f xs 始めの定義は空のリストにマッチし、空のリストを返…