2017-12-18 19 views
1

以下インポート/言語プラグマ微細つの関数を定義することは不可能である状況がありますか?

{-# language FlexibleContexts, MultiParamTypeClasses, TypeSynonymInstances, FlexibleInstances, CPP #-} 
import Data.String.Conversions 

次の二つの機能をtypechecks必要とされる(*の一種):

(++<>) :: (
    ConvertibleStrings a Text, 
    ConvertibleStrings b Text 
) 
    => a -> b -> Text 
a ++<> b = cs a <> cs b 

csappend :: (
    ConvertibleStrings a Text, 
    ConvertibleStrings b Text, 
    ConvertibleStrings Text c) 
    => a -> b -> c 
csappend a b = cs (a ++<> b) 

私は単一の関数として、上記の二つの関数を定義しようとしました:

singleFunction :: (
    ConvertibleStrings a Text, 
    ConvertibleStrings b Text, 
    ConvertibleStrings Text c, 
    Monoid Text) => a -> b -> c 
singleFunction a b = cs (cs a <> cs b) 

(下)私にエラーを与える210

*

xyz :: String 
xyz = do 
    let s = "test"      :: String 
    csappend (csappend s s :: String) s :: String -- this typechecks 
    csappend (csappend s s) s   :: String -- this does not typechecks 

。私は、エラーの理由を理解していない - 型制約は同じように見える、そしておそらく何か他のものは、エラーの原因である場合、私は思ったんだけど?

• Could not deduce (ConvertibleStrings a0 c) 
     arising from a use of ‘cs’ 
     from the context: (ConvertibleStrings a Text, 
         ConvertibleStrings b Text, 
         ConvertibleStrings Text c) 
     bound by the type signature for: 
        singleFunction :: (ConvertibleStrings a Text, 
             ConvertibleStrings b Text, ConvertibleStrings Text c) => 
            a -> b -> c 
     at /home/chris/Projects/Haskell/Hart/Hart.hs:(37,1)-(40,43) 
     The type variable ‘a0’ is ambiguous 
     Relevant bindings include 
     singleFunction :: a -> b -> c 
      (bound at /home/chris/Projects/Haskell/Hart/Hart.hs:41:1) 
     These potential instances exist: 
     instance [safe] ConvertibleStrings StrictText StrictText 
      -- Defined in ‘Data.String.Conversions’ 
     instance [safe] ConvertibleStrings StrictText String 
      -- Defined in ‘Data.String.Conversions’ 
     instance [safe] ConvertibleStrings String StrictText 
      -- Defined in ‘Data.String.Conversions’ 
     ...plus one other 
     ...plus 21 instances involving out-of-scope types 
     (use -fprint-potential-instances to see them all) 
    • In the expression: cs (cs a <> cs b) 
     In an equation for ‘singleFunction’: 
      singleFunction a b = cs (cs a <> cs b) 

/home/chris/Projects/Haskell/Hart/Hart.hs:41:26: error: 
    • Could not deduce (ConvertibleStrings a a0) 
     arising from a use of ‘cs’ 
     from the context: (ConvertibleStrings a Text, 
         ConvertibleStrings b Text, 
         ConvertibleStrings Text c) 
     bound by the type signature for: 
        singleFunction :: (ConvertibleStrings a Text, 
             ConvertibleStrings b Text, ConvertibleStrings Text c) => 
            a -> b -> c 
     at /home/chris/Projects/Haskell/Hart/Hart.hs:(37,1)-(40,43) 
     The type variable ‘a0’ is ambiguous 
     Relevant bindings include 
     a :: a (bound at /home/chris/Projects/Haskell/Hart/Hart.hs:41:16) 
     singleFunction :: a -> b -> c 
      (bound at /home/chris/Projects/Haskell/Hart/Hart.hs:41:1) 
     These potential instances exist: 
     instance [safe] ConvertibleStrings StrictText StrictText 
      -- Defined in ‘Data.String.Conversions’ 
     instance [safe] ConvertibleStrings StrictText String 
      -- Defined in ‘Data.String.Conversions’ 
     instance [safe] ConvertibleStrings String StrictText 
      -- Defined in ‘Data.String.Conversions’ 
     ...plus one other 
     ...plus 21 instances involving out-of-scope types 
     (use -fprint-potential-instances to see them all) 
    • In the first argument of ‘(<>)’, namely ‘cs a’ 
     In the first argument of ‘cs’, namely ‘(cs a <> cs b)’ 
     In the expression: cs (cs a <> cs b) 

/home/chris/Projects/Haskell/Hart/Hart.hs:41:26: error: 
    • Could not deduce (Monoid a0) arising from a use of ‘<>’ 
     from the context: (ConvertibleStrings a Text, 
         ConvertibleStrings b Text, 
         ConvertibleStrings Text c) 
     bound by the type signature for: 
        singleFunction :: (ConvertibleStrings a Text, 
             ConvertibleStrings b Text, ConvertibleStrings Text c) => 
            a -> b -> c 
     at /home/chris/Projects/Haskell/Hart/Hart.hs:(37,1)-(40,43) 
     The type variable ‘a0’ is ambiguous 
     These potential instances exist: 
     instance Monoid a => Monoid (IO a) -- Defined in ‘GHC.Base’ 
     instance Monoid Ordering -- Defined in ‘GHC.Base’ 
     instance Monoid Text -- Defined in ‘Data.Text’ 
     ...plus 8 others 
     ...plus 19 instances involving out-of-scope types 
     (use -fprint-potential-instances to see them all) 
    • In the first argument of ‘cs’, namely ‘(cs a <> cs b)’ 
     In the expression: cs (cs a <> cs b) 
     In an equation for ‘singleFunction’: 
      singleFunction a b = cs (cs a <> cs b) 

/home/chris/Projects/Haskell/Hart/Hart.hs:41:34: error: 
    • Could not deduce (ConvertibleStrings b a0) 
     arising from a use of ‘cs’ 
     from the context: (ConvertibleStrings a Text, 
         ConvertibleStrings b Text, 
         ConvertibleStrings Text c) 
     bound by the type signature for: 
        singleFunction :: (ConvertibleStrings a Text, 
             ConvertibleStrings b Text, ConvertibleStrings Text c) => 
            a -> b -> c 
     at /home/chris/Projects/Haskell/Hart/Hart.hs:(37,1)-(40,43) 
     The type variable ‘a0’ is ambiguous 
     Relevant bindings include 
     b :: b (bound at /home/chris/Projects/Haskell/Hart/Hart.hs:41:18) 
     singleFunction :: a -> b -> c 
      (bound at /home/chris/Projects/Haskell/Hart/Hart.hs:41:1) 
     These potential instances exist: 
     instance [safe] ConvertibleStrings StrictText StrictText 
      -- Defined in ‘Data.String.Conversions’ 
     instance [safe] ConvertibleStrings StrictText String 
      -- Defined in ‘Data.String.Conversions’ 
     instance [safe] ConvertibleStrings String StrictText 
      -- Defined in ‘Data.String.Conversions’ 
     ...plus one other 
     ...plus 21 instances involving out-of-scope types 
     (use -fprint-potential-instances to see them all) 
    • In the second argument of ‘(<>)’, namely ‘cs b’ 
     In the first argument of ‘cs’, namely ‘(cs a <> cs b)’ 
     In the expression: cs (cs a <> cs b) 

答えて

2

コンパイラが中間型を推論できないため、この定義は機能しません。 あなたはabTextに変換されているコンパイラに約束していますが、場所を呼び出すことによって定義されたcs a結果の型を呼び出し、唯一のサイトコンパイラを呼び出すにタイプを導出した後、制約をチェックするとき。ここでは、すぐに多型結果に再びcsを呼び出し、GHCはあなたが意味するものではどのような種類を知りません。 ++<> explicitylyは、戻り値の型でTextを持っているので

singleFunction :: (
    ConvertibleStrings a Text, 
    ConvertibleStrings b Text, 
    ConvertibleStrings Text c, 
    Monoid Text) => a -> b -> c 
singleFunction a b = cs (cs a <> cs b) 

二つの機能を持つ場合は動作します。

あなたは中間モノイドとしてTextを使いたいのであれば、あなたはより明確でなければなりません

singleFunction :: (
     ConvertibleStrings a Text, 
     ConvertibleStrings b Text, 
     ConvertibleStrings Text c) => a -> b -> c 
singleFunction a b = cs ((cs a <> cs b) :: Text) 
関連する問題