Sophie

Sophie

distrib > Fedora > 15 > i386 > by-pkgid > db1bec35f1c4ea7caaafdb647ec20fa9 > files > 56

ghc-attoparsec-devel-0.8.5.0-3.fc15.i686.rpm

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
<head>
<!-- Generated by HsColour, http://www.cs.york.ac.uk/fp/darcs/hscolour/ -->
<title>Data/Attoparsec.hs</title>
<link type='text/css' rel='stylesheet' href='hscolour.css' />
</head>
<body>
<pre><a name="line-1"></a><span class='hs-comment'>-- |</span>
<a name="line-2"></a><span class='hs-comment'>-- Module      :  Data.Attoparsec</span>
<a name="line-3"></a><span class='hs-comment'>-- Copyright   :  Bryan O'Sullivan 2007-2010</span>
<a name="line-4"></a><span class='hs-comment'>-- License     :  BSD3</span>
<a name="line-5"></a><span class='hs-comment'>-- </span>
<a name="line-6"></a><span class='hs-comment'>-- Maintainer  :  bos@serpentine.com</span>
<a name="line-7"></a><span class='hs-comment'>-- Stability   :  experimental</span>
<a name="line-8"></a><span class='hs-comment'>-- Portability :  unknown</span>
<a name="line-9"></a><span class='hs-comment'>--</span>
<a name="line-10"></a><span class='hs-comment'>-- Simple, efficient combinator parsing for 'B.ByteString' strings,</span>
<a name="line-11"></a><span class='hs-comment'>-- loosely based on the Parsec library.</span>
<a name="line-12"></a>
<a name="line-13"></a><span class='hs-keyword'>module</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>Attoparsec</span>
<a name="line-14"></a>    <span class='hs-layout'>(</span>
<a name="line-15"></a>    <span class='hs-comment'>-- * Differences from Parsec</span>
<a name="line-16"></a>    <span class='hs-comment'>-- $parsec</span>
<a name="line-17"></a>
<a name="line-18"></a>    <span class='hs-comment'>-- * Incremental input</span>
<a name="line-19"></a>    <span class='hs-comment'>-- $incremental</span>
<a name="line-20"></a>
<a name="line-21"></a>    <span class='hs-comment'>-- * Performance considerations</span>
<a name="line-22"></a>    <span class='hs-comment'>-- $performance</span>
<a name="line-23"></a>
<a name="line-24"></a>    <span class='hs-comment'>-- * Parser types</span>
<a name="line-25"></a>      <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-conid'>Parser</span>
<a name="line-26"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>Result</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span>
<a name="line-27"></a>
<a name="line-28"></a>    <span class='hs-comment'>-- ** Typeclass instances</span>
<a name="line-29"></a>    <span class='hs-comment'>-- $instances</span>
<a name="line-30"></a>
<a name="line-31"></a>    <span class='hs-comment'>-- * Running parsers</span>
<a name="line-32"></a>    <span class='hs-layout'>,</span> <span class='hs-varid'>parse</span>
<a name="line-33"></a>    <span class='hs-layout'>,</span> <span class='hs-varid'>feed</span>
<a name="line-34"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>parseOnly</span>
<a name="line-35"></a>    <span class='hs-layout'>,</span> <span class='hs-varid'>parseWith</span>
<a name="line-36"></a>    <span class='hs-layout'>,</span> <span class='hs-varid'>parseTest</span>
<a name="line-37"></a>
<a name="line-38"></a>    <span class='hs-comment'>-- ** Result conversion</span>
<a name="line-39"></a>    <span class='hs-layout'>,</span> <span class='hs-varid'>maybeResult</span>
<a name="line-40"></a>    <span class='hs-layout'>,</span> <span class='hs-varid'>eitherResult</span>
<a name="line-41"></a>
<a name="line-42"></a>    <span class='hs-comment'>-- * Combinators</span>
<a name="line-43"></a>    <span class='hs-layout'>,</span> <span class='hs-layout'>(</span><span class='hs-conid'>I</span><span class='hs-varop'>.&lt;?&gt;</span><span class='hs-layout'>)</span>
<a name="line-44"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>try</span>
<a name="line-45"></a>    <span class='hs-layout'>,</span> <span class='hs-keyword'>module</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>Attoparsec</span><span class='hs-varop'>.</span><span class='hs-conid'>Combinator</span>
<a name="line-46"></a>
<a name="line-47"></a>    <span class='hs-comment'>-- * Parsing individual bytes</span>
<a name="line-48"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>word8</span>
<a name="line-49"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>anyWord8</span>
<a name="line-50"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>notWord8</span>
<a name="line-51"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>satisfy</span>
<a name="line-52"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>satisfyWith</span>
<a name="line-53"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>skip</span>
<a name="line-54"></a>
<a name="line-55"></a>    <span class='hs-comment'>-- ** Byte classes</span>
<a name="line-56"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>inClass</span>
<a name="line-57"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>notInClass</span>
<a name="line-58"></a>
<a name="line-59"></a>    <span class='hs-comment'>-- * Efficient string handling</span>
<a name="line-60"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>string</span>
<a name="line-61"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>skipWhile</span>
<a name="line-62"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>take</span>
<a name="line-63"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>scan</span>
<a name="line-64"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>takeWhile</span>
<a name="line-65"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>takeWhile1</span>
<a name="line-66"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>takeTill</span>
<a name="line-67"></a>
<a name="line-68"></a>    <span class='hs-comment'>-- ** Consume all remaining input</span>
<a name="line-69"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>takeByteString</span>
<a name="line-70"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>takeLazyByteString</span>
<a name="line-71"></a>
<a name="line-72"></a>    <span class='hs-comment'>-- * State observation and manipulation functions</span>
<a name="line-73"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>endOfInput</span>
<a name="line-74"></a>    <span class='hs-layout'>,</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-varid'>atEnd</span>
<a name="line-75"></a>    <span class='hs-layout'>)</span> <span class='hs-keyword'>where</span>
<a name="line-76"></a>
<a name="line-77"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>Attoparsec</span><span class='hs-varop'>.</span><span class='hs-conid'>Combinator</span>
<a name="line-78"></a><span class='hs-keyword'>import</span> <span class='hs-keyword'>qualified</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>Attoparsec</span><span class='hs-varop'>.</span><span class='hs-conid'>Internal</span> <span class='hs-keyword'>as</span> <span class='hs-conid'>I</span>
<a name="line-79"></a><span class='hs-keyword'>import</span> <span class='hs-keyword'>qualified</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>ByteString</span> <span class='hs-keyword'>as</span> <span class='hs-conid'>B</span>
<a name="line-80"></a><span class='hs-keyword'>import</span> <span class='hs-conid'>Data</span><span class='hs-varop'>.</span><span class='hs-conid'>Attoparsec</span><span class='hs-varop'>.</span><span class='hs-conid'>Internal</span> <span class='hs-layout'>(</span><span class='hs-conid'>Result</span><span class='hs-layout'>(</span><span class='hs-keyglyph'>..</span><span class='hs-layout'>)</span><span class='hs-layout'>,</span> <span class='hs-varid'>parse</span><span class='hs-layout'>)</span>
<a name="line-81"></a>
<a name="line-82"></a><span class='hs-comment'>-- $parsec</span>
<a name="line-83"></a><span class='hs-comment'>--</span>
<a name="line-84"></a><span class='hs-comment'>-- Compared to Parsec 3, Attoparsec makes several tradeoffs.  It is</span>
<a name="line-85"></a><span class='hs-comment'>-- not intended for, or ideal for, all possible uses.</span>
<a name="line-86"></a><span class='hs-comment'>--</span>
<a name="line-87"></a><span class='hs-comment'>-- * While Attoparsec can consume input incrementally, Parsec cannot.</span>
<a name="line-88"></a><span class='hs-comment'>--   Incremental input is a huge deal for efficient and secure network</span>
<a name="line-89"></a><span class='hs-comment'>--   and system programming, since it gives much more control to users</span>
<a name="line-90"></a><span class='hs-comment'>--   of the library over matters such as resource usage and the I/O</span>
<a name="line-91"></a><span class='hs-comment'>--   model to use.</span>
<a name="line-92"></a><span class='hs-comment'>--</span>
<a name="line-93"></a><span class='hs-comment'>-- * Much of the performance advantage of Attoparsec is gained via</span>
<a name="line-94"></a><span class='hs-comment'>--   high-performance parsers such as 'I.takeWhile' and 'I.string'.</span>
<a name="line-95"></a><span class='hs-comment'>--   If you use complicated combinators that return lists of bytes or</span>
<a name="line-96"></a><span class='hs-comment'>--   characters, there is less performance difference between the two</span>
<a name="line-97"></a><span class='hs-comment'>--   libraries.</span>
<a name="line-98"></a><span class='hs-comment'>--</span>
<a name="line-99"></a><span class='hs-comment'>-- * Unlike Parsec 3, Attoparsec does not support being used as a</span>
<a name="line-100"></a><span class='hs-comment'>--   monad transformer.</span>
<a name="line-101"></a><span class='hs-comment'>--</span>
<a name="line-102"></a><span class='hs-comment'>-- * Attoparsec is specialised to deal only with strict 'B.ByteString'</span>
<a name="line-103"></a><span class='hs-comment'>--   input.  Efficiency concernts rule out both lists and lazy</span>
<a name="line-104"></a><span class='hs-comment'>--   bytestrings.  The usual use for lazy bytestrings would be to</span>
<a name="line-105"></a><span class='hs-comment'>--   allow consumption of very large input without a large footprint.</span>
<a name="line-106"></a><span class='hs-comment'>--   For this need, Attoparsec's incremental input provides an</span>
<a name="line-107"></a><span class='hs-comment'>--   excellent substitute, with much more control over when input</span>
<a name="line-108"></a><span class='hs-comment'>--   takes place.  If you must use lazy bytestrings, see the 'Lazy'</span>
<a name="line-109"></a><span class='hs-comment'>--   module, which feeds lazy chunks to a regular parser.</span>
<a name="line-110"></a><span class='hs-comment'>--</span>
<a name="line-111"></a><span class='hs-comment'>-- * Parsec parsers can produce more helpful error messages than</span>
<a name="line-112"></a><span class='hs-comment'>--   Attoparsec parsers.  This is a matter of focus: Attoparsec avoids</span>
<a name="line-113"></a><span class='hs-comment'>--   the extra book-keeping in favour of higher performance.</span>
<a name="line-114"></a>
<a name="line-115"></a><span class='hs-comment'>-- $incremental</span>
<a name="line-116"></a><span class='hs-comment'>--</span>
<a name="line-117"></a><span class='hs-comment'>-- Attoparsec supports incremental input, meaning that you can feed it</span>
<a name="line-118"></a><span class='hs-comment'>-- a bytestring that represents only part of the expected total amount</span>
<a name="line-119"></a><span class='hs-comment'>-- of data to parse. If your parser reaches the end of a fragment of</span>
<a name="line-120"></a><span class='hs-comment'>-- input and could consume more input, it will suspend parsing and</span>
<a name="line-121"></a><span class='hs-comment'>-- return a 'Partial' continuation.</span>
<a name="line-122"></a><span class='hs-comment'>--</span>
<a name="line-123"></a><span class='hs-comment'>-- Supplying the 'Partial' continuation with another bytestring will</span>
<a name="line-124"></a><span class='hs-comment'>-- resume parsing at the point where it was suspended. You must be</span>
<a name="line-125"></a><span class='hs-comment'>-- prepared for the result of the resumed parse to be another</span>
<a name="line-126"></a><span class='hs-comment'>-- 'Partial' continuation.</span>
<a name="line-127"></a><span class='hs-comment'>--</span>
<a name="line-128"></a><span class='hs-comment'>-- To indicate that you have no more input, supply the 'Partial'</span>
<a name="line-129"></a><span class='hs-comment'>-- continuation with an empty bytestring.</span>
<a name="line-130"></a><span class='hs-comment'>--</span>
<a name="line-131"></a><span class='hs-comment'>-- Remember that some parsing combinators will not return a result</span>
<a name="line-132"></a><span class='hs-comment'>-- until they reach the end of input.  They may thus cause 'Partial'</span>
<a name="line-133"></a><span class='hs-comment'>-- results to be returned.</span>
<a name="line-134"></a><span class='hs-comment'>--</span>
<a name="line-135"></a><span class='hs-comment'>-- If you do not need support for incremental input, consider using</span>
<a name="line-136"></a><span class='hs-comment'>-- the 'I.parseOnly' function to run your parser.  It will never</span>
<a name="line-137"></a><span class='hs-comment'>-- prompt for more input.</span>
<a name="line-138"></a>
<a name="line-139"></a><span class='hs-comment'>-- $performance</span>
<a name="line-140"></a><span class='hs-comment'>--</span>
<a name="line-141"></a><span class='hs-comment'>-- If you write an Attoparsec-based parser carefully, it can be</span>
<a name="line-142"></a><span class='hs-comment'>-- realistic to expect it to perform within a factor of 2 of a</span>
<a name="line-143"></a><span class='hs-comment'>-- hand-rolled C parser (measuring megabytes parsed per second).</span>
<a name="line-144"></a><span class='hs-comment'>--</span>
<a name="line-145"></a><span class='hs-comment'>-- To actually achieve high performance, there are a few guidelines</span>
<a name="line-146"></a><span class='hs-comment'>-- that it is useful to follow.</span>
<a name="line-147"></a><span class='hs-comment'>--</span>
<a name="line-148"></a><span class='hs-comment'>-- Use the 'B.ByteString'-oriented parsers whenever possible,</span>
<a name="line-149"></a><span class='hs-comment'>-- e.g. 'I.takeWhile1' instead of 'many1' 'I.anyWord8'.  There is</span>
<a name="line-150"></a><span class='hs-comment'>-- about a factor of 100 difference in performance between the two</span>
<a name="line-151"></a><span class='hs-comment'>-- kinds of parser.</span>
<a name="line-152"></a><span class='hs-comment'>--</span>
<a name="line-153"></a><span class='hs-comment'>-- For very simple byte-testing predicates, write them by hand instead</span>
<a name="line-154"></a><span class='hs-comment'>-- of using 'I.inClass' or 'I.notInClass'.  For instance, both of</span>
<a name="line-155"></a><span class='hs-comment'>-- these predicates test for an end-of-line byte, but the first is</span>
<a name="line-156"></a><span class='hs-comment'>-- much faster than the second:</span>
<a name="line-157"></a><span class='hs-comment'>--</span>
<a name="line-158"></a><span class='hs-comment'>-- &gt;endOfLine_fast w = w == 13 || w == 10</span>
<a name="line-159"></a><span class='hs-comment'>-- &gt;endOfLine_slow   = inClass "\r\n"</span>
<a name="line-160"></a><span class='hs-comment'>--</span>
<a name="line-161"></a><span class='hs-comment'>-- Make active use of benchmarking and profiling tools to measure,</span>
<a name="line-162"></a><span class='hs-comment'>-- find the problems with, and improve the performance of your parser.</span>
<a name="line-163"></a>
<a name="line-164"></a><span class='hs-comment'>-- $instances</span>
<a name="line-165"></a><span class='hs-comment'>--</span>
<a name="line-166"></a><span class='hs-comment'>-- The 'I.Parser' type is an instance of the following classes:</span>
<a name="line-167"></a><span class='hs-comment'>--</span>
<a name="line-168"></a><span class='hs-comment'>-- * 'Monad', where 'fail' throws an exception (i.e. fails) with an</span>
<a name="line-169"></a><span class='hs-comment'>--   error message.</span>
<a name="line-170"></a><span class='hs-comment'>--</span>
<a name="line-171"></a><span class='hs-comment'>-- * 'Functor' and 'Applicative', which follow the usual definitions.</span>
<a name="line-172"></a><span class='hs-comment'>--</span>
<a name="line-173"></a><span class='hs-comment'>-- * 'MonadPlus', where 'mzero' fails (with no error message) and</span>
<a name="line-174"></a><span class='hs-comment'>--   'mplus' executes the right-hand parser if the left-hand one</span>
<a name="line-175"></a><span class='hs-comment'>--   fails.</span>
<a name="line-176"></a><span class='hs-comment'>--</span>
<a name="line-177"></a><span class='hs-comment'>-- * 'Alternative', which follows 'MonadPlus'.</span>
<a name="line-178"></a><span class='hs-comment'>--</span>
<a name="line-179"></a><span class='hs-comment'>-- The 'Result' type is an instance of 'Functor', where 'fmap'</span>
<a name="line-180"></a><span class='hs-comment'>-- transforms the value in a 'Done' result.</span>
<a name="line-181"></a>
<a name="line-182"></a><a name="feed"></a><span class='hs-comment'>-- | If a parser has returned a 'Partial' result, supply it with more</span>
<a name="line-183"></a><span class='hs-comment'>-- input.</span>
<a name="line-184"></a><span class='hs-definition'>feed</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Result</span> <span class='hs-varid'>r</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>B</span><span class='hs-varop'>.</span><span class='hs-conid'>ByteString</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Result</span> <span class='hs-varid'>r</span>
<a name="line-185"></a><span class='hs-definition'>feed</span> <span class='hs-varid'>f</span><span class='hs-keyglyph'>@</span><span class='hs-layout'>(</span><span class='hs-conid'>Fail</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span><span class='hs-layout'>)</span> <span class='hs-keyword'>_</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>f</span>
<a name="line-186"></a><span class='hs-definition'>feed</span> <span class='hs-layout'>(</span><span class='hs-conid'>Partial</span> <span class='hs-varid'>k</span><span class='hs-layout'>)</span> <span class='hs-varid'>d</span>    <span class='hs-keyglyph'>=</span> <span class='hs-varid'>k</span> <span class='hs-varid'>d</span>
<a name="line-187"></a><span class='hs-definition'>feed</span> <span class='hs-layout'>(</span><span class='hs-conid'>Done</span> <span class='hs-varid'>bs</span> <span class='hs-varid'>r</span><span class='hs-layout'>)</span> <span class='hs-varid'>d</span>    <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Done</span> <span class='hs-layout'>(</span><span class='hs-conid'>B</span><span class='hs-varop'>.</span><span class='hs-varid'>append</span> <span class='hs-varid'>bs</span> <span class='hs-varid'>d</span><span class='hs-layout'>)</span> <span class='hs-varid'>r</span>
<a name="line-188"></a><span class='hs-comment'>{-# INLINE feed #-}</span>
<a name="line-189"></a>
<a name="line-190"></a><a name="parseTest"></a><span class='hs-comment'>-- | Run a parser and print its result to standard output.</span>
<a name="line-191"></a><span class='hs-definition'>parseTest</span> <span class='hs-keyglyph'>::</span> <span class='hs-layout'>(</span><span class='hs-conid'>Show</span> <span class='hs-varid'>a</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=&gt;</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-conid'>Parser</span> <span class='hs-varid'>a</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>B</span><span class='hs-varop'>.</span><span class='hs-conid'>ByteString</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>IO</span> <span class='hs-conid'>()</span>
<a name="line-192"></a><span class='hs-definition'>parseTest</span> <span class='hs-varid'>p</span> <span class='hs-varid'>s</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>print</span> <span class='hs-layout'>(</span><span class='hs-varid'>parse</span> <span class='hs-varid'>p</span> <span class='hs-varid'>s</span><span class='hs-layout'>)</span>
<a name="line-193"></a>
<a name="line-194"></a><a name="parseWith"></a><span class='hs-comment'>-- | Run a parser with an initial input string, and a monadic action</span>
<a name="line-195"></a><span class='hs-comment'>-- that can supply more input if needed.</span>
<a name="line-196"></a><span class='hs-definition'>parseWith</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Monad</span> <span class='hs-varid'>m</span> <span class='hs-keyglyph'>=&gt;</span>
<a name="line-197"></a>             <span class='hs-layout'>(</span><span class='hs-varid'>m</span> <span class='hs-conid'>B</span><span class='hs-varop'>.</span><span class='hs-conid'>ByteString</span><span class='hs-layout'>)</span>
<a name="line-198"></a>          <span class='hs-comment'>-- ^ An action that will be executed to provide the parser</span>
<a name="line-199"></a>          <span class='hs-comment'>-- with more input, if necessary.  The action must return an</span>
<a name="line-200"></a>          <span class='hs-comment'>-- 'B.empty' string when there is no more input available.</span>
<a name="line-201"></a>          <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>I</span><span class='hs-varop'>.</span><span class='hs-conid'>Parser</span> <span class='hs-varid'>a</span>
<a name="line-202"></a>          <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>B</span><span class='hs-varop'>.</span><span class='hs-conid'>ByteString</span>
<a name="line-203"></a>          <span class='hs-comment'>-- ^ Initial input for the parser.</span>
<a name="line-204"></a>          <span class='hs-keyglyph'>-&gt;</span> <span class='hs-varid'>m</span> <span class='hs-layout'>(</span><span class='hs-conid'>Result</span> <span class='hs-varid'>a</span><span class='hs-layout'>)</span>
<a name="line-205"></a><span class='hs-definition'>parseWith</span> <span class='hs-varid'>refill</span> <span class='hs-varid'>p</span> <span class='hs-varid'>s</span> <span class='hs-keyglyph'>=</span> <span class='hs-varid'>step</span> <span class='hs-varop'>$</span> <span class='hs-varid'>parse</span> <span class='hs-varid'>p</span> <span class='hs-varid'>s</span>
<a name="line-206"></a>  <span class='hs-keyword'>where</span> <span class='hs-varid'>step</span> <span class='hs-layout'>(</span><span class='hs-conid'>Partial</span> <span class='hs-varid'>k</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-layout'>(</span><span class='hs-varid'>step</span> <span class='hs-varop'>.</span> <span class='hs-varid'>k</span><span class='hs-layout'>)</span> <span class='hs-varop'>=&lt;&lt;</span> <span class='hs-varid'>refill</span>
<a name="line-207"></a>        <span class='hs-varid'>step</span> <span class='hs-varid'>r</span>           <span class='hs-keyglyph'>=</span> <span class='hs-varid'>return</span> <span class='hs-varid'>r</span>
<a name="line-208"></a><span class='hs-comment'>{-# INLINE parseWith #-}</span>
<a name="line-209"></a>
<a name="line-210"></a><a name="maybeResult"></a><span class='hs-comment'>-- | Convert a 'Result' value to a 'Maybe' value. A 'Partial' result</span>
<a name="line-211"></a><span class='hs-comment'>-- is treated as failure.</span>
<a name="line-212"></a><span class='hs-definition'>maybeResult</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Result</span> <span class='hs-varid'>r</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Maybe</span> <span class='hs-varid'>r</span>
<a name="line-213"></a><span class='hs-definition'>maybeResult</span> <span class='hs-layout'>(</span><span class='hs-conid'>Done</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>r</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Just</span> <span class='hs-varid'>r</span>
<a name="line-214"></a><span class='hs-definition'>maybeResult</span> <span class='hs-keyword'>_</span>          <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Nothing</span>
<a name="line-215"></a>
<a name="line-216"></a><a name="eitherResult"></a><span class='hs-comment'>-- | Convert a 'Result' value to an 'Either' value. A 'Partial' result</span>
<a name="line-217"></a><span class='hs-comment'>-- is treated as failure.</span>
<a name="line-218"></a><span class='hs-definition'>eitherResult</span> <span class='hs-keyglyph'>::</span> <span class='hs-conid'>Result</span> <span class='hs-varid'>r</span> <span class='hs-keyglyph'>-&gt;</span> <span class='hs-conid'>Either</span> <span class='hs-conid'>String</span> <span class='hs-varid'>r</span>
<a name="line-219"></a><span class='hs-definition'>eitherResult</span> <span class='hs-layout'>(</span><span class='hs-conid'>Done</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>r</span><span class='hs-layout'>)</span>     <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Right</span> <span class='hs-varid'>r</span>
<a name="line-220"></a><span class='hs-definition'>eitherResult</span> <span class='hs-layout'>(</span><span class='hs-conid'>Fail</span> <span class='hs-keyword'>_</span> <span class='hs-keyword'>_</span> <span class='hs-varid'>msg</span><span class='hs-layout'>)</span> <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Left</span> <span class='hs-varid'>msg</span>
<a name="line-221"></a><span class='hs-definition'>eitherResult</span> <span class='hs-keyword'>_</span>              <span class='hs-keyglyph'>=</span> <span class='hs-conid'>Left</span> <span class='hs-str'>"Result: incomplete input"</span>
</pre></body>
</html>