gpt4 book ai didi

iphone - 带有替换变量的 HTML 的简单 ParseKit 语法

转载 作者:可可西里 更新时间:2023-11-01 04:42:33 26 4
gpt4 key购买 nike

对于 iOS 应用程序,我想解析一个 HTML 文件,该文件可能包含用于替换的 UNIX 样式变量。例如,HTML 可能如下所示:

<html>
<head></head>
<body>
<h1>${title}</h1>
<p>${paragraph1}</p>
<img src="${image}" />
</body>
</html>

我正在尝试创建一个简单的 ParseKit 语法,它将为我提供两个回调:一个用于直通 HTML,另一个用于它检测到的变量。为此,我创建了以下语法:

@start        = Empty | content*;

content = variable | passThrough;
passThrough = /[^$]+/;
variable = '$' '{' Word closeChar;

openChar = '${';
closeChar = '}';

我至少面临两个问题:对于 variable我最初将其声明为 openChar Word closeChar ,但它没有用(我仍然不知道为什么)。第二个问题(也是更重要的)是解析器在找到 <img src"${image}" /> 时停止。 (即带引号的字符串中的变量)。

我的问题是:

  1. 如何修改语法以使其按预期工作?
  2. 使用分词器更好吗?如果是这样,我应该如何配置它?

最佳答案

这里是 ParseKit 的开发者。我会回答你的两个问题:

1) 您采用了正确的方法,但这是一个棘手的案例。有几个小陷阱,你的语法需要稍微改变一下。

我开发了一种适合我的语法:

// Tokenizer Directives
@symbolState = '"' "'"; // effectively tells the tokenizer to turn off QuoteState.
// Otherwise, variables enclosed in quotes would not be found (they'd be embedded in quoted strings).
// now single- & double-quotes will be recognized as individual symbols, not start- & end-markers for quoted strings

@symbols = '${'; // declare '${' as a multi-char symbol

@reportsWhitespaceTokens = YES; // tell the tokenizer to preserve/report whitespace

// Grammar
@start = content*;
content = passthru | variable;
passthru = /[^$].*/;
variable = start name end;
start = '${';
end = '}';
name = Word;

然后在您的汇编器中实现这两个回调:

- (void)parser:(PKParser *)p didMatchName:(PKAssembly *)a {
NSLog(@"%s %@", __PRETTY_FUNCTION__, a);
PKToken *tok = [a pop];

NSString *name = tok.stringValue;
// do something with name
}

- (void)parser:(PKParser *)p didMatchPassthru:(PKAssembly *)a {
NSLog(@"%s %@", __PRETTY_FUNCTION__, a);
PKToken *tok = [a pop];

NSMutableString *s = a.target;
if (!s) {
s = [NSMutableString string];
}

[s appendString:tok.stringValue];

a.target = s;
}

然后您的客户端/驱动程序代码将如下所示:

NSString *g = // fetch grammar
PKParser *p = [[PKParserFactory factory] parserFromGrammar:g assembler:self];
NSString *s = @"<img src=\"${image}\" />";
[p parse:s];
NSString *result = [p parse:s];
NSLog(@"result %@", result);

这将被打印:

result: <img src="" />

2) 是的,我认为对于这种相对简单的情况直接使用 Tokenizer 肯定会好得多。性能会好很多。以下是您可以如何使用 Tokenizer 完成任务:

PKTokenizer *t = [PKTokenizer tokenizerWithString:s];
[t setTokenizerState:t.symbolState from:'"' to:'"'];
[t setTokenizerState:t.symbolState from:'\'' to:'\''];
[t.symbolState add:@"${"];
t.whitespaceState.reportsWhitespaceTokens = YES;

NSMutableString *result = [NSMutableString string];

PKToken *eof = [PKToken EOFToken];
PKToken *tok = nil;
while (eof != (tok = [t nextToken])) {
if ([@"${" isEqualToString:tok.stringValue]) {
tok = [t nextToken];
NSString *varName = tok.stringValue;

// do something with variable
} else if ([@"}" isEqualToString:tok.stringValue]) {
// do nothing
} else {
[result appendString:tok.stringValue];
}
}

关于iphone - 带有替换变量的 HTML 的简单 ParseKit 语法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9299110/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com