LoginSignup
0
0

More than 5 years have passed since last update.

Database.HDBC

Posted at

SQLの実行。読めば自明な感じ。取り出した値をそれっぽい型にするにはfromSqlが使える。

module Main (main) where
import Control.Monad
import Database.HDBC
import Database.HDBC.Sqlite3

printRows :: [[SqlValue]] -> IO ()
printRows rows = forM_ rows $ \row -> do
  let row' = (fromSql :: SqlValue -> Integer) `fmap` row
  print row'

main :: IO ()
main = do
  con <- connectSqlite3 "test.db"

  _ <- run con "create table test (x int)" []
  forM_ [1 .. 10] $ \i -> do
    _ <- run con "insert into test values (?)" [SqlInt32 i]
    return ()

  st <- prepare con "select x from test"
  _ <- execute st []
  fetchAllRows st >>= printRows

  disconnect con
  return ()

結果。

[1]
[2]
[3]
[4]
[5]
[6]
[7]
[8]
[9]
[10]

fetchAllRowsの実装にはunsafeInterleaveIOが使われているので、以下のようにリストを舐める途中でfetchRowを使うと[3]が抜けてしまったりする。

  (row : row' : rows') <- fetchAllRows st
  printRows [row, row']
  _ <- fetchRow st
  printRows rows'

ドキュメントにもその辺触れられてて、例えばfinish呼んじゃうと嫌なことになるよって辺りが書いてある。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0