好的,我会更具体的
{-# LANGUAGE QuasiQuotes #-}
{-# LANGUAGE TemplateHaskell #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE TypeApplications #-}
{-# LANGUAGE ScopedTypeVariables #-}
import Database.Persist.TH
import Database.Persist.Sqlite
import Database.Esqueleto
import Control.Monad.IO.Class
share [mkPersist sqlSettings, mkMigrate "migrateAll"] [persistLowerCase|
Topic
title String
|]
main :: IO ()
main = do
runSqlite "test.sqlite" $ do
runMigration migrateAll
[Value c1] <- select $
from $ \t ->
do
return countRows
liftIO $ putStrLn $ show (c1 :: Int)
此代码会导致错误
est2.hs:26:22: error:
• Ambiguous type variable ‘a0’ arising from a use of ‘from’
prevents the constraint ‘(From
SqlQuery SqlExpr SqlBackend a0)’ from being solved.
Probable fix: use a type annotation to specify what ‘a0’ should be.
这是因为编译器不知道必须使用哪个表来计算行数。这件事可以通过类似的解决方法来完成
[Value c1] <- select $
from $ \t ->
do
orderBy [asc (t ^. TopicTitle)]
return countRows
liftIO $ putStrLn $ show (c1 :: Int)
但是,这太可怕,乏味且人为。还有另一种更简单的方法来修复此代码吗?
答案为:
我们应该声明表,其中将对行进行计数。最简单的方法是使用ScopedTypeVariables语言扩展,并在本地描述参数的类型:
[Value c2] <- select $
from $ \(_ :: SqlExpr (Entity Topic)) ->
do
return countRows