2011-10-17 28 views
4

此問題與this問題有關。試圖解析遞歸JSON,我在正確的軌道上?

下面是數據類型我希望從JSON進行:

data ProdObject = MKSpair (Text, Text) 
       | MKSLpair (Text, [Text]) 
       | MKSOpair (Text, ProdObject) 
       | MKObject ProdObject 
       | End 
       deriving Show 

Here是我處理的數據的樣本,再加上整體的概括。

這是我的實例定義,這是導致錯誤。我用this作爲參考。我不確定錯誤是在告訴我解決我的問題,還是說我沒有辦法。如果錯誤真的很直接,我想就如何修正我的類型提出一些建議,以及關於我可能做錯了什麼但尚未注意的任何建議。

instance FromJSON ProdObject where 
    parseJSON (Object o) = MKObject <$> parseJSON o 
    parseJSON (String s, String t) = MKSpair (s, t) 
    parseJSON (String s, Object o) = MKSOpair (s, MKObject <$> parseJSON o) 
    parseJSON (String s, Array a) = MKSLpair (s, V.toList a) 
    parseJSON (Done d) = End 
    parseJSON _  = mzero 

這是我現在所擁有的錯誤:

ghcifoo> :load test 
[1 of 1] Compiling Main    (test.hs, interpreted) 

test.hs:23:52: 
    Couldn't match expected type `Value' 
       with actual type `Data.Map.Map Text Value' 
    Expected type: Value 
     Actual type: Object 
    In the first argument of `parseJSON', namely `o' 
    In the second argument of `(<$>)', namely `parseJSON o' 
Failed, modules loaded: none. 

更新:我已經重做我的數據類型,如果我是對的,我已經有了一個幻象類型。如果我錯了,回到繪圖板

data ProdObject = MKSpair (Text, Text) 
       | MKSLpair (Text, [Text]) 
       | MKSOpair (Text, ProdObject) 
       | MKObject ProdObject (k,v) 
       | End 

此外,我已經在我的實例中反映了這種變化,儘管以不完整的方式。我提到這只是爲了問我是否在正確的軌道上。

parseJSON (Object (k,v)) = MKObject ... 

如果我在正確的軌道上,我想我可以找出其餘的問題,或至少問一個具體的問題。反饋任何人?

回答

1

在這個公式中:

parseJSON (Object o) = MKObject <$> parseJSON o 

o具有類型Map Text Value,但parseJSON具有類型Value -> Parser a,所以你顯然不能適用於parseJSONo

此外,您在這裏有一個錯誤類型:

parseJSON (String s, String t) = MKSpair (s, t) 

類型的parseJSONValue -> Parser a,但你想對陣(Value, Value)

這同樣適用於這一行:

parseJSON (Done d) = End 

Done不是Value類型的構造器。


我不明白你爲什麼需要ProdObject類型是遞歸的;這裏我將如何解決這個問題:

data Outer = Outer { 
    oName :: Text, 
    oProducts :: M.Map Text Inner 
} deriving Show 

data Inner = Inner { 
    iQA :: Text, 
    iVM :: Text, 
    iAvailable :: V.Vector Text 
} deriving Show 

instance FromJSON Outer where 
    parseJSON (Object o) = Outer <$> o .: "name" <*> o .: "products" 
    parseJSON _ = mzero 

instance FromJSON Inner where 
    parseJSON (Object o) = Inner <$> o .: "qa" <*> o .: "vm" <*> o .: "available" 
    parseJSON _ = mzero 

完整的代碼清單可以發現on Github

+0

我想我所擁有的是JSON對象的錯誤概念。 –

+0

我認爲它需要遞歸,因爲我交給我的數據看起來是遞歸給我的。感謝您的解決方案! –