2012-03-12 33 views
2

ParseKit冒險繼續...我的下一個障礙是試圖獲得新行符號的認可。ParseKit不符合我的EOL符號:我做錯了什麼?

這裏是我的語法:

@symbolState = '\n'; 
@start = textline*; 
textline = Any* eol; 
eol = '\n'; 

這裏是我的測試文本:

1 
2 
3 
4 
5 

文本正在被從UNIX格式(LF)行結尾一個UTF-8文本文件閱讀。我已經在Xcode(文件檢查器 - >文本設置)以及TextWrangler外部驗證了這種格式。

而這裏的相關代碼:

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

@interface FileImporterThing() 
@property (nonatomic, retain)PKParser* parser; 
- (void)parser:(PKParser *)p didMatchTextline:(PKAssembly *)a; 
- (void)parser:(PKParser *)p didMatchEol:(PKAssembly *)a; 
@end 


@implementation FileImporterThing 

@synthesize parser = _parser; 

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

    // Have also tried "textline = Any* '\n';" 
    NSString *g = @"@symbolState = '\n'; @start = textline*; textline = Any* eol; eol = '\n';"; 
    self.parser = [[PKParserFactory factory] parserFromGrammar:g assembler:self]; 

    return self; 
} 

- (void)testParse 
{ 
    // read string from UTF-8 file Unix (LF) line endings 
    // (this verified in project->file inspector->Text Settings and externally with TextWrangler) 
    NSString *path = [[NSBundle bundleForClass:[self class]] pathForResource:@"LF-test" ofType:@"parsetext"]; 
/* file contains text: 
1 
2 
3 
4 
5 

*/ 
    NSString *s = [NSString stringWithContentsOfFile:path encoding:NSUTF8StringEncoding error:nil]; 

    [self.parser parse:s]; 
} 

- (void)parser:(PKParser *)p didMatchEol:(PKAssembly *)a 
{ 
    NSLog(@"eol found");// stack = %@", [a stack]); 
} 

- (void)parser:(PKParser *)p didMatchTextline:(PKAssembly *)a 
{ 
    NSLog(@"textline matched"); 
} 

@end 

但我怕油漆只是不曬!在上面嘗試過各種各樣的變化。我不能爲了我的生活讓解析器識別換行符。我可以通過逐行讀取文件緩衝區來解決這個問題(無論如何,這可能會更高效),但仍然可以選擇匹配'\ n'。

回答

2

開發商ParseKit這裏。有兩件事情我可以貢獻:


1.

我想你的例子使用兩種或的TextMate的TextWrangler(另存爲.txt文件)中創建一個文本文件,一切似乎正常工作。按預期調用我的-parser:didMatchEol:-parser:didMatchTexline:回調。

如果這不是爲你工作,也許嘗試在內存中的字符串輸入開始是否至少,將工作:

NSString *s = @"foo bar\nbaz bat\n"; 
[parser parse:s]; 

總之,這裏是我的代碼DebugAppDelegate.m這是爲我工作用無論是在存儲器輸入或在磁盤上的輸入:

- (void)doTestGrammar { 
    NSString *g = @"@symbolState = '\n'; @start = textline*; textline = Any* eol; eol = '\n';"; 
    PKParser *p = [[PKParserFactory factory] parserFromGrammar:g assembler:self]; 
    //NSString *s = @"foo bar\nbaz bat\n"; 
    NSString *path = [@"~/Desktop/text.txt" stringByExpandingTildeInPath]; 
    NSString *s = [NSString stringWithContentsOfFile:path encoding:NSUTF8StringEncoding error:nil]; 
    [p parse:s]; 
} 

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

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

2.

我的確對你的例子工作感到有點驚訝,因爲我認爲你使用Any*生產會在生產線末尾貪婪地消耗\n標記,因此生產的eol產品不會匹配。

但是,正如我所提到的,當我運行您的示例時(對於主幹的ParseKit HEAD),這不是問題。

不過,好措施,我可能會建議改變你textline生產這樣的:

零個或多個令牌不通過匹配:

textline = ~eol* eol; 

因爲這樣生產的定義應閱讀eol,後面跟着一個符號eol

~是布爾否定運算r在ParseKit語法語法中。

對我的示例代碼進行此更改後,所有內容仍按預期工作。


如果在這兩個提示後仍然無法正常工作,請告訴我。

+1

感謝您的即時答覆託德!當然你是對的,我的錯誤,對不起 - 原來是一個愚蠢的大小寫敏感的問題,導致我的測試文件不被發現。但後來我被難倒了爲什麼我的真實代碼不工作。事實證明,對語法工作進行硬編碼,但是從文件中讀取它不會:'\ n'似乎被解釋爲不同的文字?即使把我的確切問題寫入文字也很困難,如果我從文件讀取,然後將字符串傳遞給NSLog,我會看到每個'/ n'都打印完整。但硬編碼的字符串將真正的新行發送到控制檯。有小費嗎? – Rich 2012-03-14 19:27:52

+1

如果這不是很清楚,那麼就試着修改上面的小例子,以便從文件中讀取語法。那對你有用嗎? – Rich 2012-03-14 19:33:04

+1

啊,我明白了。嗯,是的,這很棘手。也許嘗試在文法基礎版本的語法中使用'\\ n'?我會盡量找一些時間來看看今天晚些時候。可能是ParseKit中的一個錯誤,但我不確定。 – 2012-03-14 19:34:07