簡體   English   中英

Haskell 管道中的“產量”

[英]"Yield from" in Haskell Pipes

Haskell Pipes中,假設我正在編寫f:: Producer am ()並且我在關於m的 do 塊內(編輯:這沒有意義;我想要一個生產者 do 塊)。 在這個 do 塊中,我想在返回到我的 do 塊之前從g:: Producer am ()產生。 我如何做到這一點?

在我的特殊情況下, a = ()m = State s ,我的生產者正在管理一些僅影響 state.g 的分支行為g恰好只產生一次,所以在 Python 語言中,它是一個上下文管理器,它改變了一些 state,產量,然后自行清理。 因此,在 Python 中,我可以“從 g 中產生”或在g上使用@contextmanager並輸入with塊。

編輯:我正在尋找的是為回溯 function 編寫分支,比如

do
 whenM accept_this_one (lift move_to_next)
 forM_ choices \i -> 
   when (notM (bad_choice i)) (lift (select i))

g就像select i ,因此將g視為i_type -> Producer () m ()

move_to_nextselect都像上下文管理器,自行清理。 所以 state 從move_to_next的變化應該持續到(塊的末尾?在這里我很困惑。但肯定比單行更長。)這應該提供一些可以迭代的東西,它會為你管理 state。

在回答有關 state 如何受到影響的問題時, f應該合並 g 的 state 更改,如果我們說yield from g g fg可以訪問公共 state,那么它會在 Python 中這樣做。

Edit2:這是我想要的 Python 版本:

@contextmanager
def move_to_next():
    # do stuff
    yield
    # undo stuff
    return

@contextmanager
def selected(i):
    # do stuff
    yield
    # undo stuff
    return

if accept_this_one():
    cm = move_to_next()
else:
    cm = contextlib.nullcontext()
with cm:
    for i in choices:
        if not bad_choice(i):
            with selected(i):
                # Do stuff if you want
                yield

編輯3:也許這個?

select : i_type -> Prod () m ()
move_to_next : Prod () m ()
accept_this_one : m bool

do
 let x = ifM (lift accept_this_one)
           then move_to_next
           else yield
 x ~> \_ -> forM_ choices \i -> 
   when (notM (bad_choice i)) (select i)

yield (實際上,在這種情況下)具有類型a -> Producer am () 您不能在mdo塊中使用它,只能在Producer am ()do塊中使用它。 如果你需要使用一個State ,你需要先將它liftProducer

f :: Producer s (State s ()) ()
f = do
      x <- lift get
      yield x

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM