on master help sign in
Speed up unstream by splitting the loop

--HG-- extra : convert_revision : 9d1f8e8ec4a7364de9bfc63147fc5eef5476dc39

commite99387c56b5fc72860a5b93eee35ad3483e6475b authorBryan O'Sullivan <bos@serpentine.com> dateSun 15 Aug 2010, 03:02 (16 years ago) parenta8e021c
1 file changed+16−12
Data/Text/Fusion.hs+16−12
Data/Text/Fusion.hs+16−12
@@ -94,18 +94,22 @@ unstream :: Stream Char -> Text
9494unstream (Stream next0 s0 len) = I.textP (P.fst a) 0 (P.snd a)
9595 where
9696 mlen = upperBound 4 len
97− a = A.run2 (A.unsafeNew mlen >>= (\arr -> loop arr mlen s0 0))
98− loop arr !top !s !i
99− | i + 1 >= top = case next0 s of
100− Done -> return (arr, i)
101− _ -> do
102− let top' = (top `shiftL` 1) + 1
103− arr' <- A.unsafeNew top'
104− A.copy arr arr' >> loop arr' top' s i
105− | otherwise = case next0 s of
106− Done -> return (arr, i)
107− Skip s' -> loop arr top s' i
108− Yield x s' -> unsafeWrite arr i x >>= loop arr top s'
97+ a = A.run2 (A.unsafeNew mlen >>= (\arr -> outer arr mlen s0 0))
98+ outer arr top = loop
99+ where
100+ loop !s !i
101+ | i + 1 >= top = {-# SCC "unstream/resize" #-}
102+ case next0 s of
103+ Done -> return (arr, i)
104+ Skip s' -> loop s' i
105+ _ -> do
106+ let top' = (top + 1) `shiftL` 1
107+ arr' <- A.unsafeNew top'
108+ A.copy arr arr' >> outer arr' top' s i
109+ | otherwise = case next0 s of
110+ Done -> return (arr, i)
111+ Skip s' -> loop s' i
112+ Yield x s' -> unsafeWrite arr i x >>= loop s'
109113{-# INLINE [0] unstream #-}
110114{-# RULES "STREAM stream/unstream fusion" forall s. stream (unstream s) = s #-}
111115