2010-02-12 32 views
9

Đang học lex trong quá trình này, tôi đang tạo mã thông báo cho ngôn ngữ C và đang cố gắng nhận ra các nhận xét dòng đơn "//", nhưng có xung đột với toán tử phân chiaKhông thể nhận ra các nhận xét dòng đơn trong Lex

[1-9][0-9]*|0x[0-9a-fA-F][0-9a-fA-F]*   return NUMBER; 
[a-zA-Z][a-zA-Z0-9]*       return IDENT; 
/            {return DIVIDE;} 

[ \t\r\n] 
[//] 

Nhưng khi chạy ví dụ và nhập // nó nhận ra chúng là 2 toán tử phân chia. Tôi nên sửa đổi mã ở đâu. Bất kỳ đề xuất.

Edit:

Lex Code:

%{ 
#include "y.tab.h" 
%} 
%array 
%% 
if            {return IF;} 
while           {return WHILE;} 
else           {return ELSE;} 
int            {return INT;} 
return           {return RETURN;} 
\/\/[^\r\n]* 
[1-9][0-9]*|0x[0-9a-fA-F][0-9a-fA-F]*   return NUMBER; 
[a-zA-Z][a-zA-Z0-9]*       return IDENT; 

[+]            {return ADD;} 
[-]            {return SUB;} 
[<]            {return LESS;} 
[>]            {return GREAT;} 
[*]            {return MULT;} 
[/]            {return DIVIDE;} 
[;]            {return SEMICOLON;} 

\{            return LBRACE; 
\}            return RBRACE; 

[ \t\r\n] 

\(            return LPAREN; 

\)            return RPAREN; 

.            return BADCHAR; 
%% 

Sau đây là tệp tiêu đề tôi sử dụng

typedef enum {END=0, WHILE, IF, ELSE,RETURN, IDENT, LPAREN, RPAREN,INT,LBRACE,RBRACE, SEMICOLON, EQUALITY, DIVIDE, MULT, LESS, GREAT, 
ADD, SUB, NUMBER,BADCHAR} Token; 

Sau đây là các đầu vào đang chạy,

// 
/
p 
Token 16, text/
Token 16, text/
Token 16, text/
Token 5, text p 

Khi nào thì runni ng nó, bình luận được tiêu thụ và thậm chí các nhà điều hành phân chia được bỏ qua. Nhưng hãy kiểm tra khi đang nhập p, nó phân loại các toán tử được liệt kê ở trên, mà nó không nên làm.

Note: Am trying to ignore tabs, newline characters and single line comments. 

Note 2: \/\/[^\r\n]* I have understood where I committed the mistake and wanted to share this. 
+0

trả lời cho câu hỏi của bạn: http: // stackoverflow.com/questions/15423658/regular-expression-cho-single-line-comments –

Trả lời

6

Theo hướng dẫn Lex:

Các chương trình phân tích từ vựng viết với Lex chấp nhận mơ hồ thông số kỹ thuật và chọn trận đấu dài nhất có thể tại mỗi điểm đầu vào. Nếu cần thiết, đáng kể lookahead là được thực hiện trên đầu vào, nhưng đầu vào luồng sẽ được sao lưu vào cuối phân vùng hiện tại, để người dùng có quyền tự do chung để thao tác .

Vì vậy, bạn không cần phải làm bất kỳ điều gì đặc biệt - // dài hơn / vì vậy nó sẽ thích nhận xét hơn toán tử phân chia khi thấy hai. Tuy nhiên, bạn không đăng quy tắc nhận xét của mình - nó ở đâu?

Chỉnh sửa: đừng bận tâm, tôi hiểu. [//] là một lớp nhân vật. Loại bỏ các dấu ngoặc vuông. Ngoài ra, bạn sẽ muốn khớp với phần cuối của dòng - nếu không bạn sẽ chỉ cho phép nhận xét trống. Vì vậy, regex của bạn phải là một cái gì đó như:

//[^\r\n]*\r\n (điều chỉnh khi cần thiết cho các ký tự dòng mới bạn đang hỗ trợ - điều này yêu cầu một dòng mới chính xác là \r\n).

Chỉnh sửa 2: @ tur1ng mang đến một điểm tốt - dòng cuối cùng trong tệp của bạn có thể không kết thúc bằng dòng mới. Tôi nhìn nó và Lex cũng hỗ trợ <<EOF>> trong các regex của nó (xem http://pltplp.net/lex-yacc/lex.html.en). Vì vậy, bạn có thể thay đổi để:

//[^\r\n]*((\r\n)|<<EOF>>)

+0

Tôi đang cố gắng bỏ qua các tab, ký tự dòng mới và nhận xét dòng đơn – user265867

+0

Đúng vậy, tôi biết - xem bản chỉnh sửa trong câu trả lời của tôi. – danben

+0

Bạn nói đúng. shadowing của trận đấu không phải là vấn đề, tôi đã loại bỏ câu trả lời của tôi. –

Các vấn đề liên quan