haskell State 모나드를 배우려고합니다. 그래서 State Monad를 사용하여 난수 목록을 생성하는 함수를 작성했습니다.whats이 2 개의 매우 유사한 haskell 상태 계산의 차이점
여기가 첫 번째 버전입니다.
rnds :: Int -> [Int]
rnds n = evalState (help (mkStdGen 007)) []
where help prng = do s <- get
let (a, nprng) = randomR (1,6) prng
put (a:s)
if length s == n then (return s)
else (help nprng)
다음은 두 번째 버전입니다.
rnds1 :: Int -> [Int]
rnds1 n = evalState (help (mkStdGen 007)) []
where help prng = do s <- get
let (a, nprng) = randomR (1,6) prng
put (a:s)
ns <- get
if length ns == n then (return ns)
else (help nprng)
동일한 매개 변수의 경우 둘 다 동일한 출력을 제공합니다. 그러나 첫 번째 버전에서는리스트의 길이를 확인하기 위해 목록 (s
)을 참조하고 있습니다. 그러나 내가 put (a:s)
을하기 전에 s
을 획득했습니다. 그래서 내가 길이를 검사 할 때 나는 put (a:s)
을하기 전에 's'의 길이를 줄 것이라고 생각했습니다. 그러나 두 버전 모두 동일한 매개 변수가 제공되는 경우 첫 번째 버전의 출력이 두 번째 버전의 출력과 동일하기 때문에 그렇게 보이지 않습니다.
두 번째 버전은 적어도 나를 쉽게 이해할 수 있습니다. ns
목록의 길이를 확인하기 전에 먼저 새로운 업데이트 상태를 얻으려면 ns <- get
을 수행합니다.
누군가가 나에게 무슨 일이 일어 났는지 말해 줄 수 있습니까? 하스켈이 일하는 방식이나 국가 모나드 자체에 대해 뭔가 오해 한 것 같은 느낌을받습니다.
감사합니다.
do-notaion, 상태에 대한 >> =의 정의 및 가져 오기 및 붙여 넣기의 정의를 확장하십시오. http://hackage.haskell.org/packages/archive/mtl/1.1.0.2/doc /html/src/Control-Monad-State-Lazy.html#State –