Changelog
Version 1.1.0, 2020‒01‒05
-
Behaviour change:
pfloatnow parses out‐of‐range finite values as plus or minus infinity instead of returning an error. This unifies thepfloatbehaviour on all platforms after the behaviour change ofSystem.Double.Parseon .NET Core 3. - Enrico Sada modernized the F# and C# project files and the build script for the NuGet packages – thanks Enrico!
- Added SourceLink support, which was prepared and championed by Cameron Taggart – thank Cameron!
-
Maxime Didier fixed a bug in the Low‐Trust version of the
CharStreamconstructors that accept a file path argument: The stream’sNameproperty wasn’t initialized. Thanks Maxime! - Fixed missing parser definitions in the Parsing JSON section of the tutorial spotted by Josh Quintus – thanks Josh!
- Andre Wesseling fixed a parser definition in the Where is the monad section of the User’s Guide – thanks Andre!
-
Frederik K. fixed an error in the
ErrorMessagedocumentation – thanks Frederik! -
Jonathan Roeber fixed an error in the
previousCharSatisfiesNot– thanks Jonathan! -
Vegard Løkken fixed an error in the
unicodeSpacesdocumentation – thanks Vegard!
Version 1.0.3, 2017‒08‒20
- Modern solution and project files for .NET Core and VS 2017 were added to the source folders. Huge thanks to Marcus Griep for spearheading the effort to make FParsec .NET Standard compatible and contributing the new project and solution files!
- The old build script for the NuGet packages was replaced by a PowerShell script that uses the new project files.
- The FParsec NuGet package now contains assemblies for .NET Standard 1.6.
- The non‐netstandard assemblies of FParsec now reference the FSharp.Core 4.0.0.1 NuGet package, which should maximize compatibility when binding redirects aren’t available.
- A .vscode/tasks.json file with some task definitions for Visual Studio Code was added.
- The source repository was moved to GitHub.
-
Added a
stringsSepBy1parser (contributed by Robin Munn – thanks Robin!). - Added a link to the Russian translation of the tutorial by Dmitry Vlasov – thanks Dmitry!
- Fixed documentation typos. One was spotted by Brandon Dimperio, another by ZelteHonor – thanks Brandon and ZelteHonor!
-
Renamed
CLR45toAGGRESSIVE_INLININGto better match its purpose.
Version 1.0.2, 2015‒09‒27
-
replaced all uses of
Char.GetUnicodeCategorywithCharCodeInfo.GetUnicodeCategory, since the former may or may not track the current Unicode standard and the latter is the only one supported by the PCL API subset - updated the case folding, whitespace and XID property data tables to Unicode 8.0.0
- added a PCL Profile 259 version to the FParsec NuGet package
- removed the Silverlight, VS9 and VS10 solution files and the Mono Makefile
-
updated the Lex & Yacc version of the FSharpParsingSample to use the
FsLexYaccNuGet packages - fixed documentation typos (two were spotted by Francois Nardon and Patrick McDonald – thanks Francois and Patrick!)
Version 1.0.1, 2013‒06‒25
- The maintainership of the FParsec NuGet package(s) was handed over from Ryan Riley, Huw Simpson, Cameron Taggart and Khan Thompson to Stephan Tolksdorf. Thanks Ryan, Huw, Cameron and Khan for creating and maintaining the previous versions of the NuGet package!
- FParsec now has two NuGet packages, built with a new fsx script
-
fixed a bug in one of the
CharStreamconstructors (reported and patched by Andrew Smith – thanks Andrew!) -
added
USE_STATIC_MAPPING_FOR_IS_ANY_OFandUNALIGNED_READSas default compilation options in the Visual Studio projects (the default options now match the ones used by the “Big Data edition” NuGet package) - some minor code tweaking / micro‐optimizations
- fixed some minor documentation issues
Version 1.0.0, 2012‒07‒19
-
disabled code generation in
isAnyOf,isNoneOf,anyOf,skipAnyOf,noneOfandskipNoneOfby default (you can reenable it using the newUSE_STATIC_MAPPING_FOR_IS_ANY_OFcompilation option) -
annotated some
CharStreammethods with the .NET 4.5AggressiveInliningoption (see the newCLR45compilation option) - updated case folding and XID property tables to Unicode 6.1.0
- fixed two documentation typos (spotted by Rasmus Meldgaard and Kurt Schelfthout – thanks Rasmus and Kurt!)
Version 0.9.2, 2012‒03‒09
- fixed compilation in Visual Studio 11 Beta
-
added missing
ReturnFrommember toparsebuilder object (reported by Kurt Schelfthout and Tomas Petricek – thanks Kurt and Tomas!) -
added workaround for .NET
ConsoleStreamissue (reported by Alexander Kahl – thanks Alexander!) -
set
AllowPartiallyTrustedCallersandSecurityTransparentassembly attributes in LOW_TRUST NET4 build (as suggested by hammett – thanks hammett!) - changed encoding of FParsecCS/Strings.cs to UTF‐8 (with signature) to fix Visual Studio build on machines with Japanese locale (the encoding issue was reported on http://d.hatena.ne.jp/ZOETROPE – thank you!)
- fixed some documentation issues (incorporating feedback from Alexander Gelkin, Antoine Latter and Stephen Swensen – thanks Alexander, Antoine and Stephen!)
- add link to the Japanese translation of the tutorial by Gab_km (thanks Gab_km!)
Version 0.9.1, 2011‒05‒22
- added /nooptimizationdata compiler flag as a workaround for an F# comiler issue (reported by Michael Giagnocavo – thanks Michael!)
- fixed an issue in the JSON sample (reported by Ryan Riley – thanks Ryan!)
- fixed the error message formatting when an error line contains unaccounted newlines or ends with a combining character sequence
-
added warning to installation notes that the
regexparser doesn’t work on Mono (reported by Laurent Le Brun – thanks Laurent!) - fixed some documentation issues (one of which was reported by Michael Giagnocavo – thanks Michael!)
Version 0.9.0, 2011‒04‒26
- Highlights
-
- a new tutorial and user’s guide
- 2x performance improvements due to a refactored low‐level API
-
new
identifierparser for parsing identifiers based on Unicode XID syntax -
new
StaticMappingmodule for compiling static key to value mappings into optimized functions (supportschar,intandstringas key types)
- Changes to high‐level API
-
-
the modules
FParsed.Primitives,FParsec.CharParsersandFParsec.Errorare now automatically opened when theFParsecnamespace is opened -
new combinators
.>>.,.>>.?,notEmpty,stringsSepBy -
new parsers
identifier,unicodeSpaces[1],notFollowedByEof -
whitespaceandunicodeWhitespacehas been removed -
unicodeNewlineno longer recognizes the form feed char'\f'('\u000C') as a newline character -
some variants of
many,sepBy,sepEndByandmanyTillhave been removed -
the
...FoldApplyinline variants ofmany,sepBy,sepEndByandmanyTillhave been consolidated in theFParsec.Primitives.Inlinehelper class -
sequence parsers now throw a
System.InvalidOperationExceptioninstead of aSystem.Exceptionto prevent an infinite loop -
anyOf,noneOf,isAnyOfandisNoneOfnow use runtime code generation (except in the Low‐Trust version). If you run into performance issues after upgrading to version 0.9, make sure that you don’t unnecessarily recreateanyOfornoneOfparsers, see here and here. -
pstring,notFollowedByStringand similar parsers now have optimized code paths for argument strings with only 1 char -
the behaviour of
manyCharsandmanyCharsTilland their variants has slightly changed -
the skip variants of
manyCharsandmanyCharsTillhave been removed -
Some renamings and function signature changes:
Table 1.3.8.1 Old New restOfLinerestOfLine trueskipRestOfLineskipRestOfLine trueskipToEndOfLineskipRestOfLine falseskipToString[CI] str nskipCharsTillString[CI] str false ncharsTillString[CI] str ncharsTillString[CI] str true nskipCharsTillString[CI] str nskipCharsTillString[CI] str true nfollowedByChar chrif chr = '\r' || chr = '\n' then followedByNewline else followedByString (string chr)
notFollowedByChar chrif chr = '\r' || chr = '\n' then notFollowedByNewline else notFollowedByString (string chr)
currentCharSatisfies fnextCharSatisfies fnextCharSatisfies fnext2CharsSatisfy (fun _ c1 -> f c1)
-
OperatorPrecedenceParserhas changed:-
all types have been moved from the
FParsec.OperatorPrecedenceParsermodule into the mainFParsecnamespace -
the operator types
InfixOp,PrefixOp, … classes have been renamed toInfixOperator,PrefixOperator, … -
Assochas been renamed toAssociativity - the “whitespace‐parser” argument of the operator types has been generalized into an “after‐string‐parser” argument
-
if you previously used the
InfixOp',PrefixOp', … constructors to supply a mapping that read the text position of the parsed operator from the passedStateinstance, read this -
the
AddOperatorsmethod has been removed, callAddOperatorinstead -
the
OperatorConflictErrorFormatterreplaced theOperatorConflictHandler
-
all types have been moved from the
-
the modules
-
Removed variants of
many,sepBy,sepEndByandmanyTill -
If you previously used these variants, you can easily define them in your own code using the
|>>combinator, as documented in the reference documentation for the previous version. For example:let manyRev p = many p |>> List.rev let manyFold acc0 f p = many p |>> List.fold f acc0 let manyReduce f defVal p = (many1 p |>> List.reduce f) <|>% defVal.
If you need optimized implementations, you can define them using the new
Inlinehelper class. The file Doc/misc/removed‐many‐variants.fs contains optimized definitions for all removed variants. -
Details on changes to
manyChars,manyCharsTilland their variants -
The behaviour of all variants of
manyCharsandmanyCharsTillhas slightly changed. NowmanyChars cpis equivalent tomany cp, except that it returns a string instead of char list. Previously,manyChars cpbehaved likemany (attempt cp), i.e. it automatically backtracked if the char parser had failed after consuming input. The same change has been made to the behaviour of all other variants ofmanyCharsandmanyCharsTill. The new behaviour is more consistent with the rest of the libary and allows a faster implementation with the new low‐level API.There probably aren’t many parsers that relied on the old behaviour.
The behaviour change made the
skipvariants ofmanyCharandmanyCharsTillobsolete, since e.g.skipManyCharswould do exactly the same asskipMany cp. Hence, theskipvariants have been removed. - Changes to low‐level API
-
-
The old
CharStreamandStateclasses have been merged into a singleCharStreamclass with a mutable interface. -
Parserfunctions now take aCharStream<'u>instance as the input argument. -
The
Replytype has been moved to the mainFParsecnamespace and no longer has aStatemember. -
Parser state comparisons are now done with the help of the
CharStream’sStateTag. -
Various methods from the old
CharStream.IteratorandStatetypes have been renamed in the newCharStreamclass and have new signatures:-
When you adapt old code, the following changes require particular attention:
-
the old
Iterator.Readmethods did not advance the input stream position, but the newCharStream.Readnow do (as is the expected behaviour in traditional stream classes) -
the old
Read()is equivalent to the newPeek() -
the old
Read(int)is equivalent to the newPeekString(int) -
the old
Peek()is equivalent to the new (and old)Peek(1)
-
the old
-
More renamings:
-
Next,Advance?Skip -
_Increment,_Decrement?SkipAndPeek -
SkipRestOfLinewith string output ?ReadRestOfLine -
SkipCharOrNewlineswith string output ?ReadCharsOrNewlines -
SkipToString?SkipCharsOrNewlinesUntilString -
SkipToStringCI?SkipCharsOrNewlinesUntilCaseFoldedString -
ReadUntil?ReadFrom -
CharStream.FoldCase?Text.FoldCase -
CharStream.NormalizeNewlines?Text.NormalizeNewlines
-
-
-
New
CharStreammethods:-
Skipmethods with char and string arguments -
SkipUnicodeWhitespace -
SkipNewlineThenWhitespace
-
-
The
ErrorMessageandErrorMessageListtypes are now defined in the C# library part. This allows us to implement full parsers in C#. TheFParsec.Errormodule contains type abbreviations and active patters that provide the familiar interface to F# clients. -
All error messages used by built‐in FParsec parsers are now defined in the C# classes
FParsec.StringsandFParsec.Errors. This should simplify customization and internationalization efforts.
-
The old
- Background on low‐level API changes
-
Previously parsers were implemented as functions operating on an immutable parser state in the form of a
Stateinstance. A parser function received aStateinstance as the input and returned aStateinstance as part of its return value. SinceStateinstances were immutable, a parser function had to create a newStateinstance to advance the input stream, e.g. by callingstate.Advance(2).This architecture was motivated by the desire to provide an API as “functional” as possible, an API that shields users from the underlying imperative/mutable nature of input streams. When FParsec originally started as a relatively close port of Haskell’s Parsec library, this design felt like a natural fit for a functional parser library. However, later, when FParsec moved away from its Parsec roots (to improve performance and provide more features), it became increasingly clear that the immutable
CharStream‐State‐design was the main obstacle preventing FParsec from reaching the performance of hand‐optimized recursive‐descent parsers.Initial tests with some quick prototypes revealed that the allocation and garbage collection of temporary
Stateinstances took up to 50% or more of the run time of typical parsers – even though theStateclass was already heavily optimized. These tests also indicated that consolidating the stream and state classes into a classical imperative stream class simplified the overall library implementation and made the library source code more accessible to new users.The main drawback of the API change is that it requires modifications to practically all low‐level parser code. Another drawback is that backtracking is slightly less convenient with the new low‐level API (as the parser state has to be explicitly saved and restored, while previously one could just continue with an old state instance).
Since FParsec’s high‐level API is only minimally affected by the change, the advantages seem to outweigh the costs.
Version 0.8.x, no release
- New features/ improvements
-
-
case‐insensitive matching with
pstringCI,charsTillStringCI, etc. (using the Unicode 1‐to‐1 case folding mappings for chars in the BMP) -
various new parsers and combinators, including
restOfLine,skipToString,manySatisfyMinMax,manyStrings,withSkippedString -
new functions
runParserOnSubstringandrunParserOnSubstream - various performance improvements
- Silverlight support
- F# 1.9.6.16 compatibility
-
case‐insensitive matching with
- Design changes
-
-
standardized on a single input stream type (
FParsec.CharStream) and a single concrete parser state type (FParsec.State) -
refactored the
Reply<_,_>,ErrorMessageandParserErrortypes:- error replies now also contain a complete
State -
whether a parser has changed the state is now determined by checking the input and the output state for equality, instead of testing the
Consumedflag -
replaced the
Reply<_,_>.Flagswith aStatusfield -
replaced the various helper functions for constructing a
Replywith three overloadedReply<_,_>constructors (with different arities)
- error replies now also contain a complete
-
all char parsers are now “newline aware”, i.e. they normalize any of the three standard newline representations (
"\n","\r\n","\r") to “n” and they properly increment the line count whenever they parse a newline; this means that the behaviour of almost all char parsers has changed with regard to how newline chars are handled
-
standardized on a single input stream type (
- Bug fixes
-
-
The
CharStreamclass now uses the serialization API to persist the decoder state for backtracking purposes. Previously it relied on the decoder loosing its state at block boundaries after a certain sequence of method calls. The previous approach works in practice for the .NET decoders of the standard unicode encodings and for simple stateless encodings like ASCII and ANSI, but it relies on undocumented behaviour and it does not work reliably for encodings like GB18030, ISO‐2022 or ISCII. -
In previous FParsec versions the
CharStreamfile path/System.IO.Stream constructors failed with anIndexOutOfRangeexception when the file/stream was empty and encoding detection was not turned off (reported by Vesa Karvonen ‐ thanks Vesa!). -
In previous FParsec versions the
NumberLiteral.Stringreturned by thenumberLiteralparser included parsed suffix chars despite the documentation claiming the opposite. (The testing code was buggy too.) Applications that rely on this behaviour can now use the newNumberLiteralOptions.IncludeSuffixCharsInStringto force thenumberLiteralparser to include any suffix chars in the returned string. -
Fixed behaviour of
>>=?,>>?and.>>?when second parser fails with fatal error without changing the parser state. -
Fixed behaviour of
nextCharSatisfies[Not]when current “char” is a"\r\n"newline.
-
The
- Other breaking changes
-
-
renamed the module
CharParsertoCharParsers -
moved
CharParser.OperatorPrecedenceParserinto separate module
-
FParsec.Primitives:-
subtle change: renamed
messagetofailandfailtofailFatally -
renamed
pair,tripleandquadtotuple2,tuple3andtuple4 -
renamed
manyFoldLefttomanyFoldand changed the argument order of the accumulator and function argument - removed
manyFoldRight -
renamed
counttoparrayand changed the return type, renamedskipCounttoskipArray -
renamed
followedByandnotFollowedBytofollowedByLandnotFollowedByLand introducedfollowedByandnotFollowedByfunctions that take no second argument -
moved
ParserResult<_>toCharParsersand changed constructor arguments - removed applyParser
-
removed
|>>=, now>>=automatically uses an optimized branch for uncurried functions -
removed
endByandendBy1(endBy p sepcan be replaced withmany (p .>> sep)andendBy1 p sepwithmany1 (p .>> sep))
-
subtle change: renamed
-
FParsec.CharParsers:-
renamed
manyTillStringtocharsTillString - removed
applyParserfrom the public interface -
removed
getIndex,skip,registerNL,extract,regexp(these low‐level operations should be done directly through theState<_>/CharStream.Iteratorinterface) - removed
anyCharOrNL(no longer needed, see design changes above) -
removed
nSatisfy(can be replaced withmanySatisfyMinMax) -
removed
unicodeDigitandunicodeNumber(can be replaced withsatisfy System.Char.IsDigitandsatisfy System.Char.IsNumber) -
moved the helper functions
expectedError,unexpectedErroretc. into theErrormodule
-
renamed
-
FParsec.CharStream:- string constructor takes more arguments
-
Iterator.Peek(i)now returns theEndOfStreamCharchar instead of throwing an exception if the char peeked at lies before the beginning of the stream
-
renamed the module
Version 0.7.3.1, 2009‒02‒26
-
Fixed a bug in
CharParser.normalizeNewlines/CharStream.NormalizeNewlines. This bug also affected theskippedandmanyTillStringparsers, which internaly callnormalizeNewlinesto normalize the returned string.The bug was reported by Greg Chapman ‐ thanks Greg!
When given a multi‐line string in which the lines are delimited by
"\r\n"but the last line does not end in a newline, the buggynormalizeNewlinesreplaced the chars on the last line with'\n'chars.
-
Changed the signature of
Helper.SkipOverWhitespace.
Version 0.7.3, 2008‒12‒08
Breaking changes (all of which should have little or no impact on existing code bases):
-
CharStream.Iteratorinstances now compare equal if and only if they belong to the sameCharStreamand point to the same index (previously they compared only equal if their internal representations were identical) -
the constructor argument of
Error.otherErroris now expected to be comparable with F#’s structural comparison functioncompare, see http://research.microsoft.com/fsharp/manual/spec2.aspx#_Toc207785725 -
the signature of the second
ParserError.ToStringoverload has changed -
CharParser.errorToStringandprintErrorLinehave been deprecated
New features:
-
reimplemented the error formatting code in
FParsec.Error -
added new
State<_>.AdvanceToandCharStream.Iterator.Advanceoverloads -
slightly modified the error reporting in
Primitives.sepEndBy - some documentation fixes
Version 0.7.2, 2008‒11‒17
-
added
CharParser.OperatorPrecedenceParser -
changed the overflow checking in
pint32such that it will not be affected by an expected future change in F#’sint32 -> uint64conversion behaviour -
added
CharParser.pint16,puint16,pint8,puint8 -
changed the signatures in CharParser.fsi to use the
Parser<_,_>type abbreviation -
fixed outdated documentation of
CharParser.expectedError - some minor optimizations
Version 0.7.1, 2008‒09‒29
Breaking changes:
-
renamed
Primitives.Reply._tagmember toFlagsand gave it a proper enumeration type -
CharParser.Stateis now a reference type -
Removed
CharParser.State.Flagsmember -
deprecated
Primitives.reconstructError
Version 0.7.0.1, 2008‒09‒23
Breaking change:
-
changed the case of the
FParsec.Error.Posmembers (This wasn’t already done in 0.7 because of an oversight.)
Version 0.7.0, 2008‒09‒13
Bugfixes:
-
made
FParsec.Error.PosIComparable to preventParserError.ToStringfrom throwing an exception under rare circumstances -
corrected the argument checking for some
CharStream.Iteratormethods for very large arguments
New features:
- compatibility with the F# CTP release
-
a configurable parser for number literals:
CharParser.numberLiteral -
CharParser.pfloatnow also parsesNaN,Infinityand hexadecimal floating point literals as supported by IEEE754r, C99 and Java (but different from the hex representation supported by F#) -
new helper functions
CharParser.floatToHexString,floatOfHexString,float32ToHexStringandfloat32OfHexString -
integer parsers:
Charparser.pint32,puint64,puint32,puint64 - new sample: a JSON parser
- various optimizations and some code cleanup
-
new
CharStream.IteratormembersReadUntil,IncrementandDecrement -
new
StatememberAdvanceTo -
new function
Primitives.createParserForwardedToRef -
new combinator
|>>=inPrimitives
Breaking changes:
-
renamed the parsers
charandstringtopcharandpstring(This is in deference to the built‐in F# functionscharandstring, which weren’t yet around when the first version of FParsec was released.) -
changed the case of the properties of the
ReplyandStatetypes (This reflects the emerging consensus in the F# community that all public members of types should be named in PascalCase.) -
deprecated
State.AdvanceNL(use the 3 parameter Advance overload instead) -
deprecated the
Primitiveshelper functionsisOk,isEmpty, … (theReplypropertiesIsOk,IsEmpty,… should be used instead) -
deprecated the
CharParserhelper functionsmatchChar,readChar, … (theState.ItermethodsMatch,Read, … should be used instead) -
deprecated
Primitives.option,<|>$should be used instead -
made
CharParser.CharListinternal (If you need this helper class for your code, just copy the implementation to your source.) -
State.Flags()now has more bits (and less bits are reset on a position change)
Version 0.6.0, 2008‒05‒20
-
fixed a bug in
manyTillString(the code keeping track of newlines was buggy) -
fixed a bug in
CharParser.<?>(the error reporting was inconsistent withPrimitives.<?>in the rare case where<?>is applied inside anattempt (...) <?> labelclause to a parser that returns anEmptyOkreply) - various changes for F# 1.9.4.15
-
added
skippedparser toCharParser -
added
nextCharSatifiesNot,prevCharSatifiesNot,currCharSatisfies,currCharSatisfiesNottoCharParsermodule; the behaviours of the existingnextCharSatisfiesandprevCharSatisfieswere slightly changed (see fparsec.html for more details) -
added
TryWithandTryFinallymembers toPrimitivs.ParserCombinator -
added
tripleandquadparsers toPrimitivesmodule -
set
CompilationRepresentationFlags.PermitNullforError.ParserError - various optimizations
-
some documentation fixes, including corrections for the docs of the
CharParsererror generation helper functions (expectedErroretc.)
Version 0.5.1, 2008‒01‒20
-
added
pipe2,pipe3andpipe4primitives -
replaced
countandskipCountprimitives with optimized versions -
minor optimizations in
spacesandspaces1 - added
pfloatchar parser - minor documentation fixes
Version 0.5.0, 2008‒01‒15
-
Major design change: all lazy computations were removed and the types
OutputandReplyunified. The new implementation is considerably simpler and also compiles with F# 1.9.3.7. - Fixed a bug in build.bat (reported by Santosh Zachariah ‐ thanks Santosh!)
Version 0.4.4, 2008‒01‒13
- fixed a minor issue in CharParser.attempt
-
added
.>>!and>>.!primitives -
added
skipManySatisfyandskipMany1Satisfychar parsers
Version 0.4.3, 2008‒01‒12
-
fixed bugs in the CharParser versions of
<?>andattempt. - added
>>?primitive -
added
skipSatisfyandskipSatisfyLchar parsers - minor documentation fixes
Version 0.4.2, 2008‒01‒04
-
performance improvements in
CharStream.Iterator - minor documentation fixes
Version 0.4.1, 2008‒01‒02
- documentation fixes
- new sample application: a parser for Parsing Expression Grammars
-
newlineandunicodeNewlinenow return'\n', instead of 1 or 2 -
added
whitespaceparser and changedunicodeWhitespace -
added
spacesparser (equivalent toskipManyChars whitespace) -
removed
newlineReplparameter frommanyTillString -
added
skipManyTillandskipManyCharsTill - generalized types of skipManyChars and skipManyChars1
Version 0.4.0, 2007‒12‒30
Initial public release