Haskell - 在 Prelude.sequence 函数的结果之间插入线程处理
Haskell - Inserting a thread dealy between the results of Prelude.sequence function
我有一些代码看起来像这样
listOfIOByteStrings = simpleHttp <$> apiLinks :: [IO ByteString]
其中 apiLinks
是调用某些 API 函数的链接列表。
我也有这个功能
z = sequence listOfIOByteStrings
sequence
有这种类型 sequence :: Monad m => t (m a) -> m (t a)
我想做的是在每个 ByteString
的评估之间添加一个线程延迟。
我正在考虑使用 threadDelay
threadDelay :: Int -> IO ()
这就是我最终要做的事情
listOfContent <- z
pPrint $ filteredTitles . onlyElems . parseXML <$> listOfContent
哪里
parseXML :: ByteString -> [Content]
onlyElems :: [Content] -> [Element]
和
filteredTitles :: [Element] -> [String]
在序列结果之间应用线程延迟就像这样
printing (filteredTitles . onlyElems . parseXML (bytestring of link1))...
delay of 1 sec...
printing (filteredTitles . onlyElems . parseXML (bytestring of link2))...
delay of 1 sec...
printing (filteredTitles . onlyElems . parseXML (bytestring of link3))...
delay of 1 sec...
我不确定我应该怎么做。
我不太了解您管道中的所有类型,因此请将其视为可以充实的粗略草图。首先,您不想过早调用 sequence
。暂时保留 IO Bytestring
值列表。
接下来,您需要一些函数(根据 filteredTitles . onlyElems . parseXML
定义)需要一个 单个 Bytestring
和 returns 一个 IO ()
。如果 pPrint
是写类型,这可能只是
process :: IO ByteString -> IO ()
process ibs = do
bs <- ibs
pPrint (filteredTitles . onlyElems . parseXML $ bs)
map process (apiLinks >>= simpleHttp)
应生成 [IO ()]
类型的列表。这可能会以不那么笨拙的方式重写,但是 现在 我们可以找到答案的核心,即使用 intersperse
在最终排序之前插入您的线程延迟[IO ()]
得到 IO [()]
.
import Data.List
let results = map process (apiLinks >>= simpleHttp)
actions = intersperse (threadDelay 1) results
in sequence actions
intersperse :: a -> [a] -> [a]
通过在其第二个元素的每个元素之间插入其第一个参数来工作。使用字符串的简单示例:
> intersperse '-' "abc"
"a-b-c"
其中一种方法是使用 forM_
作为
...
do listOfContent <- z
forM_ listOfContent $
\content -> do pPrint $ (filteredTitles . onlyElems . parseXML) content
threadDelay 1000000
我有一些代码看起来像这样
listOfIOByteStrings = simpleHttp <$> apiLinks :: [IO ByteString]
其中 apiLinks
是调用某些 API 函数的链接列表。
我也有这个功能
z = sequence listOfIOByteStrings
sequence
有这种类型 sequence :: Monad m => t (m a) -> m (t a)
我想做的是在每个 ByteString
的评估之间添加一个线程延迟。
我正在考虑使用 threadDelay
threadDelay :: Int -> IO ()
这就是我最终要做的事情
listOfContent <- z
pPrint $ filteredTitles . onlyElems . parseXML <$> listOfContent
哪里
parseXML :: ByteString -> [Content]
onlyElems :: [Content] -> [Element]
和
filteredTitles :: [Element] -> [String]
在序列结果之间应用线程延迟就像这样
printing (filteredTitles . onlyElems . parseXML (bytestring of link1))...
delay of 1 sec...
printing (filteredTitles . onlyElems . parseXML (bytestring of link2))...
delay of 1 sec...
printing (filteredTitles . onlyElems . parseXML (bytestring of link3))...
delay of 1 sec...
我不确定我应该怎么做。
我不太了解您管道中的所有类型,因此请将其视为可以充实的粗略草图。首先,您不想过早调用 sequence
。暂时保留 IO Bytestring
值列表。
接下来,您需要一些函数(根据 filteredTitles . onlyElems . parseXML
定义)需要一个 单个 Bytestring
和 returns 一个 IO ()
。如果 pPrint
是写类型,这可能只是
process :: IO ByteString -> IO ()
process ibs = do
bs <- ibs
pPrint (filteredTitles . onlyElems . parseXML $ bs)
map process (apiLinks >>= simpleHttp)
应生成 [IO ()]
类型的列表。这可能会以不那么笨拙的方式重写,但是 现在 我们可以找到答案的核心,即使用 intersperse
在最终排序之前插入您的线程延迟[IO ()]
得到 IO [()]
.
import Data.List
let results = map process (apiLinks >>= simpleHttp)
actions = intersperse (threadDelay 1) results
in sequence actions
intersperse :: a -> [a] -> [a]
通过在其第二个元素的每个元素之间插入其第一个参数来工作。使用字符串的简单示例:
> intersperse '-' "abc"
"a-b-c"
其中一种方法是使用 forM_
作为
...
do listOfContent <- z
forM_ listOfContent $
\content -> do pPrint $ (filteredTitles . onlyElems . parseXML) content
threadDelay 1000000