Commits

Georg Brandl committed bf21dc7 Merge

Comments (0)

Files changed (2)

pygments/lexers/_mapping.py

     'EvoqueHtmlLexer': ('pygments.lexers.templates', 'HTML+Evoque', ('html+evoque',), ('*.html',), ('text/html+evoque',)),
     'EvoqueLexer': ('pygments.lexers.templates', 'Evoque', ('evoque',), ('*.evoque',), ('application/x-evoque',)),
     'EvoqueXmlLexer': ('pygments.lexers.templates', 'XML+Evoque', ('xml+evoque',), ('*.xml',), ('application/xml+evoque',)),
+    'FSharpLexer': ('pygments.lexers.dotnet', 'FSharp', ('fsharp',), ('*.fs', '*.fsi'), ('text/x-fsharp',)),
     'FactorLexer': ('pygments.lexers.agile', 'Factor', ('factor',), ('*.factor',), ('text/x-factor',)),
     'FancyLexer': ('pygments.lexers.agile', 'Fancy', ('fancy', 'fy'), ('*.fy', '*.fancypack'), ('text/x-fancysrc',)),
     'FelixLexer': ('pygments.lexers.compiled', 'Felix', ('felix', 'flx'), ('*.flx', '*.flxh'), ('text/x-felix',)),

pygments/lexers/dotnet.py

 """
 import re
 
-from pygments.lexer import RegexLexer, DelegatingLexer, bygroups, using, this
+from pygments.lexer import RegexLexer, DelegatingLexer, bygroups, include, \
+     using, this
 from pygments.token import Punctuation, \
      Text, Comment, Operator, Keyword, Name, String, Number, Literal, Other
 from pygments.util import get_choice_opt
 from pygments.lexers.web import XmlLexer
 
 __all__ = ['CSharpLexer', 'NemerleLexer', 'BooLexer', 'VbNetLexer',
-           'CSharpAspxLexer', 'VbNetAspxLexer']
+           'CSharpAspxLexer', 'VbNetAspxLexer', 'FSharpLexer']
 
 
 def _escape(st):
             return 0.2
         elif re.search(r'script[^>]+language=["\']vb', text, re.I) is not None:
             return 0.15
+
+
+# Very close to functional.OcamlLexer
+class FSharpLexer(RegexLexer):
+    """
+    For the F# language.
+    """
+
+    name = 'FSharp'
+    aliases = ['fsharp']
+    filenames = ['*.fs', '*.fsi']
+    mimetypes = ['text/x-fsharp']
+
+    keywords = [
+      'abstract', 'and', 'as', 'assert', 'base', 'begin', 'class',
+      'default', 'delegate', 'do', 'do!', 'done', 'downcast',
+      'downto', 'elif', 'else', 'end', 'exception', 'extern',
+      'false', 'finally', 'for', 'fun', 'function', 'global', 'if',
+      'in', 'inherit', 'inline', 'interface', 'internal', 'lazy',
+      'let', 'let!', 'match', 'member', 'module', 'mutable',
+      'namespace', 'new', 'null', 'of', 'open', 'or', 'override',
+      'private', 'public', 'rec', 'return', 'return!', 'sig',
+      'static', 'struct', 'then', 'to', 'true', 'try', 'type',
+      'upcast', 'use', 'use!', 'val', 'void', 'when', 'while',
+      'with', 'yield', 'yield!'
+    ]
+    keyopts = [
+      '!=','#','&','&&','\(','\)','\*','\+',',','-',
+      '-\.','->','\.','\.\.',':','::',':=',':>',';',';;','<',
+      '<-','>','>]','\?','\?\?','\[','\[<','\[>','\[\|',
+      ']','_','`','{','\|','\|]','}','~','<@','=','@>'
+    ]
+
+    operators = r'[!$%&*+\./:<=>?@^|~-]'
+    word_operators = ['and', 'asr', 'land', 'lor', 'lsl', 'lxor', 'mod', 'not', 'or']
+    prefix_syms = r'[!?~]'
+    infix_syms = r'[=<>@^|&+\*/$%-]'
+    primitives = ['unit', 'int', 'float', 'bool', 'string', 'char', 'list', 'array',
+                  'byte', 'sbyte', 'int16', 'uint16', 'uint32', 'int64', 'uint64'
+                  'nativeint', 'unativeint', 'decimal', 'void', 'float32', 'single',
+                  'double']
+
+    tokens = {
+        'escape-sequence': [
+            (r'\\[\\\"\'ntbr]', String.Escape),
+            (r'\\[0-9]{3}', String.Escape),
+            (r'\\x[0-9a-fA-F]{2}', String.Escape),
+        ],
+        'root': [
+            (r'\s+', Text),
+            (r'false|true|\(\)|\[\]', Name.Builtin.Pseudo),
+            (r'\b([A-Z][A-Za-z0-9_\']*)(?=\s*\.)',
+             Name.Namespace, 'dotted'),
+            (r'\b([A-Z][A-Za-z0-9_\']*)', Name.Class),
+            (r'//.*?\n', Comment.Single),
+            (r'\(\*', Comment, 'comment'),
+            (r'\b(%s)\b' % '|'.join(keywords), Keyword),
+            (r'(%s)' % '|'.join(keyopts), Operator),
+            (r'(%s|%s)?%s' % (infix_syms, prefix_syms, operators), Operator),
+            (r'\b(%s)\b' % '|'.join(word_operators), Operator.Word),
+            (r'\b(%s)\b' % '|'.join(primitives), Keyword.Type),
+
+            (r'#[ \t]*(if|endif|else|line|nowarn|light)\b.*?\n',
+             Comment.Preproc),
+
+            (r"[^\W\d][\w']*", Name),
+
+            (r'\d[\d_]*', Number.Integer),
+            (r'0[xX][\da-fA-F][\da-fA-F_]*', Number.Hex),
+            (r'0[oO][0-7][0-7_]*', Number.Oct),
+            (r'0[bB][01][01_]*', Number.Binary),
+            (r'-?\d[\d_]*(.[\d_]*)?([eE][+\-]?\d[\d_]*)', Number.Float),
+
+            (r"'(?:(\\[\\\"'ntbr ])|(\\[0-9]{3})|(\\x[0-9a-fA-F]{2}))'",
+             String.Char),
+            (r"'.'", String.Char),
+            (r"'", Keyword), # a stray quote is another syntax element
+
+            (r'"', String.Double, 'string'),
+
+            (r'[~?][a-z][\w\']*:', Name.Variable),
+        ],
+        'comment': [
+            (r'[^(*)]+', Comment),
+            (r'\(\*', Comment, '#push'),
+            (r'\*\)', Comment, '#pop'),
+            (r'[(*)]', Comment),
+        ],
+        'string': [
+            (r'[^\\"]+', String.Double),
+            include('escape-sequence'),
+            (r'\\\n', String.Double),
+            (r'"', String.Double, '#pop'),
+        ],
+        'dotted': [
+            (r'\s+', Text),
+            (r'\.', Punctuation),
+            (r'[A-Z][A-Za-z0-9_\']*(?=\s*\.)', Name.Namespace),
+            (r'[A-Z][A-Za-z0-9_\']*', Name.Class, '#pop'),
+            (r'[a-z_][A-Za-z0-9_\']*', Name, '#pop'),
+        ],
+    }