3

在掌握了 ParseKit 语法语法(在演示应用程序中玩耍)之后,我现在正试图让我自己的迷你演示工作,但到目前为止还没有取得多大成功。汇编程序回调没有被调用。

下面是相关代码的精简版。运行时testParse解析器似乎可以正常工作,并且可以正确地将我的字符串与我的anything产品匹配(在演示中也可以使用),但是 didMatchAnything: 只是没有被调用。

#import <Foundation/Foundation.h>

@class PKParser;

@interface FileParserThing : NSObject {
    PKParser* _parser;
}
- (void)testParse;
@end


#import <ParseKit/ParseKit.h>
#import "FileParserThing.h"

@interface FileParserThing ()
@property (nonatomic, retain)PKParser* parser;
- (void)didMatchAnything:(PKAssembly *)a;
@end

@implementation FileParserThing

@synthesize parser = _parser;

-(id)init
{
    if (!(self = [super init])) return nil;

    NSString *g = @"@start = anything; anything = Any+;";
    self.parser = [[PKParserFactory factory] parserFromGrammar:g assembler:self];

    return self;
}

- (void)testParse
{
    NSString *s = @"Foo Bar";
    NSLog(@"test parse with: %@", s);
    [self.parser parse:s];
}

- (void)didMatchAnything:(PKAssembly *)a
{
    NSLog(@"Hooray!");
}

@end

在 ParseKit 代码中挖掘,我可以看到 PKParser 的第 129 行

[assembler performSelector:assemblerSelector withObject:self withObject:a];

没有被执行,因为assembler是 nil。这反过来又把我带到了解析器工厂;我对正在发生的事情的理解开始失败。

免责声明;我知道,我可能需要阅读The Book,但一次只有一件事。我想先做一个小的概念证明,然后再花 30 只老鼠买一本书,如果我的项目不是初学者,我可能永远不会再读 :)

4

1 回答 1

5

ParseKit 的开发者在这里。

不久前,我更改了 Assembler 回调的签名以接受两个参数:

  1. 匹配当前令牌的解析器。
  2. 包含输入解析的当前状态的程序集

以前,只有一个论点:大会。

我不确定文档是否已完全更新以反映这一点。

所以我怀疑如果你只是将你的 Assembler 回调方法更改为此,它将起作用:

- (void)parser:(PKParser *)p didMatchAnything:(PKAssembly *)a {
    NSLog(@"%s %@", __PRETTY_FUNCTION__, a);
}

如果没有,请告诉我,我将帮助进一步调试。


背景:我做了这个改变,因为我遇到了一个情况,我的 Assembler 回调确实需要检查刚刚进行当前匹配的 Parser。

它还更紧密地对齐了Delegate回调的强大 Cocoa 约定,该约定始终将委托对象作为其第一个参数。事后看来,我有点希望我已经将ParseKit 中的Assemblers的整个概念重命名为Delegates。因为用 Cocoa 的说法,这基本上就是汇编程序。

于 2012-03-10T15:45:36.820 回答