我正在使用返回JSON响应的外部API.其中一个响应是一个对象数组,这些对象由其中的字段值标识.我在理解如何使用Aeson解析这样的JSON响应时遇到了一些麻烦.
这是我的问题的简化版本:
newtype Content = Content { content :: [Media] } deriving (Generic)
instance FromJSON Content
data Media =
Video { objectClass :: Text
, title :: Text } |
AudioBook { objectClass :: Text
, title :: Text }
Run Code Online (Sandbox Code Playgroud)
在API文档中,可以说对象可以通过字段objectClass来识别,该字段对于我们的Video对象具有值"video"而对于我们的AudioBook具有 "有声读物" 等等.示例JSON:
[{objectClass: "video", title: "Some title"}
,{objectClass: "audiobook", title: "Other title"}]
Run Code Online (Sandbox Code Playgroud)
问题是如何使用Aeson来接近这种类型的JSON?
instance FromJSON Media where
parseJSON (Object x) = ???
Run Code Online (Sandbox Code Playgroud) 我还在学习Haskell的基础知识,目前正在将一些Java代码移植到Haskell.我目前的问题是使用Network.Socket.ByteString的UDP recvFrom.
问题在于这种方法:
public abstract SocketAddress receive(ByteBuffer dst) throws IOException
Receives a datagram via this channel.
If a datagram is immediately available, or if this channel
is in blocking mode and one eventually becomes available,
then the datagram is copied into the given byte buffer and
its source address is returned. If this channel is in
non-blocking mode and a datagram is not immediately available
then this method immediately returns null.
Run Code Online (Sandbox Code Playgroud)
问题是,当我使用Network.Socket.ByteString.recvFrom时,我的代码块会在此时等待数据包到来.它不会返回类似于Maybe的内容来指示是否收到了某些内容(在Java中,当没有数据可用时返回null时)
我找到了这个帖子:https://mail.haskell.org/pipermail/haskell-cafe/2010-August/082725.html …
我有兴趣为我的 monad 转换器堆栈获得缩放功能,该功能定义如下:
newtype Awesome a = Awesome (StateT AwesomeState (ExceptT B.ByteString IO) a)
deriving (Functor, Applicative, Monad
, MonadIO, MonadError B.ByteString
, MonadState AwesomeState)
Run Code Online (Sandbox Code Playgroud)
我的AwesomeState是深度嵌套的记录,因此使用缩放将极大地帮助我更新某些字段。但问题是,对于我的 newtype 来说,zoom 不能开箱即用。
Couldn't match type ‘Control.Lens.Internal.Zoom.Zoomed Awesome’
with ‘Control.Lens.Internal.Zoom.Zoomed m0’
Run Code Online (Sandbox Code Playgroud)
我找到了一个示例,说明如何制作 Zoom 的自定义 newtype RWST 实例,但尝试使其适应我的 newtype 没有结果
可以在此处找到 RWST 示例:http ://lpaste.net/87737
有没有一种方法可以开始在我的 monad 变压器堆栈中使用缩放?为了实现这一目标,我需要做什么?如果我应该像 RWST 示例中那样实现 Zoomed/Zoom,那么我需要一个指示如何执行此操作的指针,因为我尝试并失败了。
我有点困惑,不知道在哪里寻找下面的"问题"的信息/解释(这本身不是问题,但更多的是我不明白背后有什么问题的情况):
我有一个带StateT的monad变换器堆栈.在我的函数中的某个时刻,我想将我的一小部分状态绑定到局部变量中,所以我可以引用它而不是写出我感兴趣的状态块的整个路径.这就是我的意思意思:
{-# LANGUAGE ScopedTypeVariables #-}
...
someFunction :: MyMonad ()
someFunction = do
...
let x :: Traversal' MyState MyDataT = myState.clients.ix clientIdx.someData.ix dataIdx
...
Run Code Online (Sandbox Code Playgroud)
现在这不编译:
Couldn't match type ‘(MyDataT -> f0 MyDataT)
-> MyState -> f0 MyState’
with ‘forall (f :: * -> *).
Control.Applicative.Applicative f =>
(MyDataT -> f MyDataT) -> MyState -> f MyState’
Run Code Online (Sandbox Code Playgroud)
但是如果我将这个数据块的引用移动到一个函数中,那么一切都可以编译好:
someFunction :: MyMonad ()
someFunction = do
...
let x = clientData clientIdx dataIdx
...
where clientData :: Int …Run Code Online (Sandbox Code Playgroud) haskell ×4
haskell-lens ×2
aeson ×1
json ×1
networking ×1
newtype ×1
nonblocking ×1
parsing ×1
sockets ×1
traversal ×1
udp ×1
zooming ×1