json在haskell中解析

前端之家收集整理的这篇文章主要介绍了json在haskell中解析前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我试图解析 haskell中的 JSON数据.经历了大量的网站,这是我能够达到的最远的.
data Address = Address { house :: Integer,street :: String,city :: String,state :: String,zip :: Integer } deriving (Show)
data Person = Person { name :: String,age :: Integer,address :: Address } deriving (Show)

getName :: Person -> String
getName (Person n _ _) = n

getAddress :: Person -> Address
getAddress (Person _ _ a) = a

getState :: Address -> String
getState (Address _ _ _ s _) = s

我在一个文件ex.hs中写,并将其加载到ghci – >

Prelude> import Text.JSON
Prelude Text.JSON> :load ex
Main Text.JSON> let aa = "{\"name\": \"some body\",\"age\" : 23,\"address\" : {\"house\" : 285,\"street\" : \"7th Ave.\",\"city\" : \"New York\",\"state\" : \"New York\",\"zip\" : 10001}}"
...> decode aa :: Result JSValue

它返回

Ok (JSObject (JSONObject {fromJSObject = [("name",JSString (JSONString {fromJSString = "some body"})),("age",JSRational False (23 % 1)),("address",JSObject (JSONObject {fromJSObject = [("house",JSRational False (285 % 1)),("street",JSString (JSONString {fromJSString = "7th Ave."})),("city",JSString (JSONString {fromJSString = "New York"})),("state",("zip",JSRational False (10001 % 1))]}))]}))

不用说,看起来很冗长(可怕).我试过

...> decode aa :: Result Person

它给了我一个错误.如何从这个json字符串中填充Person数据结构的实例?例如,我应该怎么做才能获得JSON字符串中的人的状态?

解决方法

问题是Text.JSON不知道如何将JSON数据转换为
您的人员数据类型.要做到这一点,你需要做个人和
JSON类型实例,或者可以使用Text.JSON.Generic和
DeriveDataTypeable扩展为你做的工作.

泛型

Text.JSON.Generic方法将读取基于JSON的结构
数据类型的结构.

{-# LANGUAGE DeriveDataTypeable #-}
import           Text.JSON.Generic

data Address = Address
    { house  :: Integer,city   :: String,state  :: String,zip    :: Integer
    } deriving (Show,Data,Typeable)

data Person = Person
    { name    :: String,age     :: Integer,address :: Address
    } deriving (Show,Typeable)

aa :: String
aa = "{\"name\": \"some body\",\"zip\" : 10001}}"

main = print (decodeJSON aa :: Person)

只要您不介意匹配字段的名称,此方法的工作效果非常好
在您的数据结构中,您的JSON格式.

除此之外,您不需要编写getName,getAddress,
和getState.您的记录类型中的字段名称是accesor
功能.

∀ x. x ⊦ :t house
house :: Address -> Integer
∀ x. x ⊦ :t address
address :: Person -> Address

JSON实例

或者,你可以走高路,实现自己的实例
JSON类.

import           Control.Applicative
import           Control.Monad
import           Text.JSON

data Address = Address
    { house  :: Integer,state  :: String
    -- Renamed so as not to conflict with zip from Prelude,zipC   :: Integer
    } deriving (Show)

data Person = Person
    { name    :: String,address :: Address
    } deriving (Show)

aa :: String
aa = "{\"name\": \"some body\",\"zip\" : 10001}}"

-- For convenience
(!) :: (JSON a) => JSObject JSValue -> String -> Result a
(!) = flip valFromObj

instance JSON Address where
    -- Keep the compiler quiet
    showJSON = undefined

    readJSON (JSObject obj) =
        Address        <$>
        obj ! "house"  <*>
        obj ! "street" <*>
        obj ! "city"   <*>
        obj ! "state"  <*>
        obj ! "zip"
    readJSON _ = mzero

instance JSON Person where
    -- Keep the compiler quiet
    showJSON = undefined

    readJSON (JSObject obj) =
        Person       <$>
        obj ! "name" <*>
        obj ! "age"  <*>
        obj ! "address"
    readJSON _ = mzero

main = print (decode aa :: Result Person)

这样可以很好地利用结果类型是一个很容易应用的事实
链接在一起查询JSObject值.

这是一个更多的工作,但它给你更多的控制的结构JSON,如果你必须处理将导致风格指南的JSON由于奇怪的字段名称而导致违规.

原文链接:https://www.f2er.com/js/151889.html

猜你在找的JavaScript相关文章