Как извлечь необработанное содержимое (включая комментарии) в скобки в определенных ситуациях? ⇐ C#

Место общения программистов C#
Anonymous
Как извлечь необработанное содержимое (включая комментарии) в скобки в определенных ситуациях?

Сообщение Anonymous »

Я пытаюсь написать грамматику Antlr4 для формата файла .asl (LivesPlit Autosplating Language). Это формат сценария с одним пользовательским блоком () и несколько блоков действия (, init и т. д.), которые содержат необработанные C#. Содержание этих действий должно оставаться точно так же, как они были написаны; Комментарии, отступы, включены пробелы.

Код: Выделить всё

state("ProcessName") {
int a : 0x0;
}

startup {
// } {
/* { */
{
int foo = 123;
}
}
У меня нет проблем с состоянием анализа . Тем не менее, я изо всех сил пытаюсь выяснить, как сохранить необработанное содержимое других блоков.

ожидаемый вывод для запуска < /code> должен быть: < /p>

Код: Выделить всё

  // } {
/* { */
{
int foo = 123;
}
< /code>
Но я получаю: < /p>

// } {
/* { */
{
int foo = 123;
}
}
< /code>
Вы можете видеть, что есть ведущая новая линия и прицельная скоба.CSharpLexer.g4

Код: Выделить всё

lexer grammar CSharpLexer;

// Numbers
HexadecimalIntegerLiteral
: ('0x' | '0X') HEXADECIMAL_DIGIT+
;

fragment HEXADECIMAL_DIGIT
: [a-fA-F]
| DECIMAL_DIGIT
;

DecimalIntegerLiteral
: DECIMAL_DIGIT+
;

fragment DECIMAL_DIGIT
: [0-9]
;

// Strings
StringLiteral
: RegularStringLiteral
| VerbatimStringLiteral
;

RegularStringLiteral
: '"' REGULAR_STRING_LITERAL_CHARACTER*? '"'
;

fragment SIMPLE_ESCAPE_SEQUENCE
: '\\' [0abfnrtv'"\\]
;

fragment HEXADECIMAL_ESCAPE_SEQUENCE
: '\\x' HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT? HEXADECIMAL_DIGIT? HEXADECIMAL_DIGIT?
;

fragment UNICODE_ESCAPE_SEQUENCE
: '\\u' HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT
| '\\U' HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT HEXADECIMAL_DIGIT
;

fragment SINGLE_CHARACTER
: ~['\\\u000D\u000A\u0085\u2028\u2029]
;

fragment REGULAR_STRING_LITERAL_CHARACTER
: HEXADECIMAL_ESCAPE_SEQUENCE
| SIMPLE_ESCAPE_SEQUENCE
| UNICODE_ESCAPE_SEQUENCE
| SINGLE_CHARACTER
;

VerbatimStringLiteral
: '@"' VERBATIM_STRING_LITERAL_CHARACTER*? '"'
;

fragment VERBATIM_STRING_LITERAL_CHARACTER
: '""'
| ~'"'
;

// Identifiers
Identifier
: '@'? IDENTIFIER_START_CHARACTER IDENTIFIER_PART_CHARACTER*
;

fragment COMBINING_CHARACTER
: [\p{Mn}\p{Mc}]
| UNICODE_ESCAPE_SEQUENCE
;

fragment CONNECTING_CHARACTER
: [\p{Pc}]
| UNICODE_ESCAPE_SEQUENCE
;

fragment DECIMAL_DIGIT_CHARACTER
: [\p{Nd}]
| UNICODE_ESCAPE_SEQUENCE
;

fragment FORMATTING_CHARACTER
: [\p{Cf}]
| UNICODE_ESCAPE_SEQUENCE
;

fragment LETTER_CHARACTER
: [\p{L}\p{Nl}]
| UNICODE_ESCAPE_SEQUENCE
;

fragment IDENTIFIER_START_CHARACTER
: LETTER_CHARACTER
| '_'
;

fragment IDENTIFIER_PART_CHARACTER
: COMBINING_CHARACTER
| CONNECTING_CHARACTER
| DECIMAL_DIGIT_CHARACTER
| FORMATTING_CHARACTER
| LETTER_CHARACTER
;
< /code>
AslLexer.g4

Код: Выделить всё

lexer grammar AslLexer;

import CSharpLexer;

tokens {
TAction
}

StateName
: 'state'
;

ActionName
: ('startup'
| 'init'
| 'update'
| 'start'
| 'split'
| 'reset'
| 'onStart'
| 'onSplit'
| 'onReset'
| 'gameTime'
| 'isLoading'
| 'exit'
| 'shutdown')
-> pushMode(action)
;

TypeName
: 'sbyte'
| 'byte'
| 'bool'
| 'short'
| 'ushort'
| 'char'
| 'int'
| 'uint'
| 'long'
| 'ulong'
| 'float'
| 'double'
| 'decimal'
| 'byte' DECIMAL_DIGIT+
| 'string' DECIMAL_DIGIT+
;

// Comments
SingleLineComment
: '//' ~[\r\n]* -> channel(HIDDEN)
;

DelimitedComment
: '/*' .*? '*/' -> channel(HIDDEN)
;

// Punctuation
OBrace
: '{'
;

CBrace
: '}'
;

OParen
: '('
;

CParen
: ')'
;

Comma
: ','
;

Colon
: ':'
;

Semi
: ';'
;

WhiteSpace
: [ \t\r\n\u000C\u00A0]+
-> skip
;

Anything
: .
;

mode action;

AComment
: '//' ~[\r\n]*
-> more
;

ADelimitedComment
: '/*' .*? '*/'
-> more
;

AOBrace
: '{' {
if (ModeStack.Count == 1)
{
Skip();
}
else
{
More();
}
}
-> pushMode(action)
;

ACBrace
: '}' {
if (ModeStack.Count >  2)
{
More();
PopMode();
}
else
{
Type = TAction;
PopMode();
PopMode();
}
}
;

AAnything
: .
-> more
;
< /code>
AslParser.g4

Код: Выделить всё

parser grammar AslParser;

options {
tokenVocab = AslLexer;
}

script
: stateSection?
actions
EOF
;

stateSection
: stateDeclaration OBrace stateVariables? CBrace
;

stateDeclaration
: StateName OParen ProcessName=StringLiteral CParen
| StateName OParen ProcessName=StringLiteral Comma Version=StringLiteral CParen
;

stateVariables
: stateVariable (Semi stateVariable)* Semi?
;

stateVariable
: TypeName Name=Identifier Colon (Module=StringLiteral Comma)? Offset=HexadecimalIntegerLiteral (Comma Offset=HexadecimalIntegerLiteral)*
;

actions
: TAction+
;
< /code>
I'm also getting these issues for the sample input above:
mismatched input 'a' expecting Identifier
extraneous input 'startup' expecting TAction
< /code>
What's the issue here?
As a side note: is it possible to extract the contents between the quotation marks of a StringLiteral
? Например, для stringliteral "processname" я хотел бы получить справедливое processname . Я могу сделать это в своем коде, конечно, но подумал, что спрошу.

Подробнее здесь: https://stackoverflow.com/questions/795 ... ific-situa

Вернуться в «C#»