কোনও লেক্সার তার পার্সারে ফেরত টোকেনগুলির ডেটাটাইপ কী হওয়া উচিত?


21

শিরোনামে যেমন বলা হয়েছে, কোনও লেক্সারের পার্সারটি কোন ডেটা টাইপের ফিরতি / ফিরিয়ে দেওয়া উচিত? উইকিপিডিয়ায় যে লেজিকাল অ্যানালাইসিস নিবন্ধটি পড়ার সময় , এটি বলেছিল:

কম্পিউটার সায়েন্সে লেক্সিকাল এনালাইসিস হ'ল অক্ষরের ক্রমকে রূপান্তর করার প্রক্রিয়া (যেমন কোনও কম্পিউটার প্রোগ্রাম বা ওয়েব পৃষ্ঠায়) টোকেনের ক্রম ( চিহ্নিত "অর্থ" সহ স্ট্রিং ) রূপান্তরিত করার প্রক্রিয়া ।

তবে উপরোক্ত বক্তব্যের সম্পূর্ণ বিপরীতে, যখন আমি অন্য সাইটে জিজ্ঞাসা করেছি ( আপনি যদি কৌতূহলী হন তবে কোড পর্যালোচনা ) উত্তর দেওয়া হয়েছিল, ব্যক্তি উত্তর দিয়েছিল যে:

লেক্সার সাধারণত স্ট্রিং পড়েন এবং এটিকে লেক্সেমির স্ট্রিমে রূপান্তরিত করুন। লেক্সেমিকে কেবল সংখ্যার স্ট্রিম হওয়া দরকার ।

এবং তিনি এই দৃশ্য দিয়েছেন:

nl_output => 256
output    => 257
<string>  => 258

পরবর্তীতে নিবন্ধে তিনি উল্লেখ করেছেন Flex, ইতিমধ্যে বিদ্যমান একজন লেক্সার, এবং বলেছিলেন যে এর সাথে 'বিধি' লেখাই হাতের সাহায্যে কোনও লেক্সার লেখার চেয়ে সহজ হবে। তিনি আমাকে এই উদাহরণ দিতে এগিয়ে গেলেন:

Space              [ \r\n\t]
QuotedString       "[^"]*"
%%
nl_output          {return 256;}
output             {return 257;}
{QuotedString}     {return 258;}
{Space}            {/* Ignore */}
.                  {error("Unmatched character");}
%%

আমার অন্তর্দৃষ্টি আরও আরও তথ্য পেতে, আমি ফ্লেক্স সম্পর্কে উইকিপিডিয়া নিবন্ধটি পড়ি । ফ্লেক্স নিবন্ধটি দেখিয়েছিল যে আপনি টোকেন সহ, সিনট্যাক্স নিয়মের একটি সেট নিম্নলিখিত উপায়ে সংজ্ঞায়িত করতে পারেন:

digit         [0-9]
letter        [a-zA-Z]

%%
"+"                  { return PLUS;       }
"-"                  { return MINUS;      }
"*"                  { return TIMES;      }
"/"                  { return SLASH;      }
"("                  { return LPAREN;     }
")"                  { return RPAREN;     }
";"                  { return SEMICOLON;  }
","                  { return COMMA;      }
"."                  { return PERIOD;     }
":="                 { return BECOMES;    }
"="                  { return EQL;        }
"<>"                 { return NEQ;        }
"<"                  { return LSS;        }
">"                  { return GTR;        }
"<="                 { return LEQ;        }
">="                 { return GEQ;        }
"begin"              { return BEGINSYM;   }
"call"               { return CALLSYM;    }
"const"              { return CONSTSYM;   }
"do"                 { return DOSYM;      }
"end"                { return ENDSYM;     }
"if"                 { return IFSYM;      }
"odd"                { return ODDSYM;     }
"procedure"          { return PROCSYM;    }
"then"               { return THENSYM;    }
"var"                { return VARSYM;     }
"while"              { return WHILESYM;   }

আমার কাছে মনে হচ্ছে যে ফ্লেক্স লেক্সারটি কীওয়ার্ড-টোকেনের স্ট্রিং ফিরিয়ে দিচ্ছে। তবে এটি নির্দিষ্ট সংখ্যার সমান প্রত্যাবর্তনকারী হতে পারে।

যদি লেক্সার নম্বরগুলি ফেরত দিতে যাচ্ছিল, তবে এটি স্ট্রিং লিটারেলগুলি কীভাবে পড়বে? একটি সংখ্যা ফেরত দেওয়া একক কীওয়ার্ডের জন্য ঠিক আছে, তবে আপনি কীভাবে কোনও স্ট্রিং মোকাবেলা করবেন? লেক্সারের স্ট্রিংটিকে বাইনারি সংখ্যায় রূপান্তর করতে হবে না এবং তারপরে পার্সার সংখ্যাকে আবার স্ট্রিংয়ে রূপান্তর করতে পারে। লেক্সারের স্ট্রিংগুলি ফিরে আসার পক্ষে এটি আরও অনেক যৌক্তিক (এবং সহজ) বলে মনে হয় এবং তারপরে পার্সার যেকোন সংখ্যক স্ট্রিং লিটারেলকে আসল সংখ্যায় রূপান্তর করতে দেয়।

বা লেসচারটি উভয়কেই ফিরিয়ে দিতে পারে? আমি সি ++ তে একটি সাধারণ লেক্সার লেখার চেষ্টা করছি, যা আপনাকে আপনার ফাংশনগুলির জন্য কেবল একটি রিটার্ন টাইপ করতে দেয়। এইভাবে আমাকে আমার প্রশ্ন জিজ্ঞাসা করতে নেতৃত্ব দিচ্ছে।

আমার প্রশ্নটিকে অনুচ্ছেদে ঘনীভূত করার জন্য: যখন কোনও লেক্সার লেখার সময় এবং ধরে নেওয়া যায় যে এটি কেবলমাত্র একটি ডেটা টাইপ (স্ট্রিং বা সংখ্যা) ফেরত দিতে পারে যা আরও যুক্তিযুক্ত পছন্দ হবে?


লেক্সার আপনি যা বলবেন তা ফিরে আসে। যদি আপনার ডিজাইনে সংখ্যার জন্য কল করা হয়, তবে এটি নম্বরগুলি ফিরিয়ে দেবে। স্পষ্টতই, স্ট্রিং লিটারেলগুলি উপস্থাপন করতে এর চেয়ে কিছুটা বেশি প্রয়োজন। আরও দেখুন নাম্বার এবং স্ট্রিংগুলিকে পার্স করা কোনও লেক্সারের কাজ? নোট করুন যে স্ট্রিং লিটারেলগুলি সাধারণত "ভাষা উপাদান" হিসাবে বিবেচিত হয় না।
রবার্ট হার্ভে

@ রবার্টহারভে তাই আপনি কি স্ট্রিংকে আক্ষরিক বাইনারি সংখ্যায় রূপান্তর করবেন?
খ্রিস্টান ডিন

আমি যেমন এটি বুঝতে পেরেছি তেমন লেক্সারের উদ্দেশ্য হ'ল ভাষা উপাদানগুলি (যেমন কীওয়ার্ড, অপারেটর এবং এর মতো) নেওয়া এবং সেগুলিকে টোকনে রূপান্তর করা। যেমন, উদ্ধৃত স্ট্রিংগুলি লেকসারের পক্ষে কোনও আগ্রহী নয়, কারণ এগুলি ভাষা উপাদান নয়। যদিও আমি নিজে কখনও কোনও লিক্সার লিখিনি, তবে আমি কল্পনা করব যে উদ্ধৃত স্ট্রিংটি কেবল অপরিবর্তিত (উদ্ধৃতি সহ) এর মধ্য দিয়ে গেছে।
রবার্ট হার্ভে

সুতরাং, আপনার বক্তব্যটি কী যে লেক্সার স্ট্রিং লিটারালগুলি পড়ে না বা যত্ন করে না। এবং সুতরাং পার্সারকে অবশ্যই এই স্ট্রিং আক্ষরিক সন্ধান করতে হবে? এটা খুব বিভ্রান্তিকর।
খ্রিস্টান ডিন

আপনি এটি পড়তে কয়েক মিনিট ব্যয় করতে চাইতে পারেন: en.wikedia.org/wiki/Lexical_analysis
রবার্ট হার্ভে

উত্তর:


10

সাধারণত, আপনি যদি কোনও ভাষা প্রক্রিয়াজাতকরণ এবং পার্সিংয়ের পরেও প্রক্রিয়াজাত করে থাকেন তবে আপনার লেক্সিকাল টোকেনগুলির একটি সংজ্ঞা পাওয়া গেছে, যেমন:

NUMBER ::= [0-9]+
ID     ::= [a-Z]+, except for keywords
IF     ::= 'if'
LPAREN ::= '('
RPAREN ::= ')'
COMMA  ::= ','
LBRACE ::= '{'
RBRACE ::= '}'
SEMICOLON ::= ';'
...

পার্সারটির জন্য আপনার একটি ব্যাকরণ রয়েছে:

STATEMENT ::= IF LPAREN EXPR RPAREN STATEMENT
            | LBRACE STATEMENT BRACE
            | EXPR SEMICOLON
EXPR      ::= ID
            | NUMBER
            | ID LPAREN EXPRS RPAREN
...

আপনার লেক্সার ইনপুট স্ট্রিম নেয় এবং টোকেনের একটি স্ট্রিম উত্পাদন করে। টোকেনের স্রোত একটি পার্স গাছ লাগানোর জন্য পার্সার গ্রাস করে। কিছু কিছু ক্ষেত্রে, শুধু বুদ্ধিমান টাইপ টোকেন হয় যথেষ্ট (যেমন, LPAREN, RBRACE জন্য), কিন্তু কিছু ক্ষেত্রে, আপনি প্রকৃত প্রয়োজন হবে মান যে টোকেন সঙ্গে সংশ্লিষ্ট। উদাহরণস্বরূপ, আপনি যখন কোনও আইডি টোকেনের মুখোমুখি হন, আপনি কোন আইডেন্টিফারটি রেফারেন্স করার চেষ্টা করছেন তা নির্ধারণ করার চেষ্টা করার পরে আপনি পরে আসল অক্ষরগুলি চাইবেন that

সুতরাং, আপনার কাছে সাধারণত কম-বেশি কিছু রয়েছে:

enum TokenType {
  NUMBER, ID, IF, LPAREN, RPAREN, ...;
}

class Token {
  TokenType type;
  String value;
}

সুতরাং যখন লেশার একটি টোকেন ফিরিয়ে দেয়, আপনি জানেন যে এটি কী ধরণের (যা আপনার বিশ্লেষণের জন্য প্রয়োজন), এবং এটি থেকে উদ্ভূত বর্ণগুলির ক্রম (যা পরে আপনাকে স্ট্রিং এবং সংখ্যাসূচক, শনাক্তকারী, ইত্যাদি)। আপনি দু'টি মান ফিরিয়ে দিচ্ছেন বলে মনে হতে পারে, যেহেতু আপনি খুব সাধারণ সমষ্টিগত প্রকারটি ফিরিয়ে দিচ্ছেন তবে আপনার উভয় অংশই সত্যই দরকার। সর্বোপরি, আপনি নিম্নলিখিত প্রোগ্রামগুলি আলাদাভাবে আচরণ করতে চাই:

if (2 > 0) {
  print("2 > 0");
}
if (0 > 2) {
  print("0 > 2");
}

এগুলি টোকেন ধরণের একই ক্রম উত্পাদন করে : IF, LPAREN, NUMBER, GREATER_THAN, NUMBER, RPAREN, LBRACE, ID, LPAREN, STRING, RPAREN, SEMICOLON, RBRACE। তার মানে তারাও একই পার্স করে। তবে আপনি যখন পার্স গাছের সাথে আসলে কিছু করছেন, আপনি খেয়াল করবেন যে প্রথম সংখ্যার মান '2' (বা '0') এবং দ্বিতীয় সংখ্যার মান '0' (বা '2) '), এবং স্ট্রিংয়ের মান হ'ল' 2> 0 '(বা' 0> 2 ')।


আপনার বক্তব্যটি আমি বেশিরভাগই পেয়েছি তবে কীভাবে তা String valueপূরণ হবে? এটি একটি স্ট্রিং বা একটি সংখ্যা দিয়ে পূর্ণ হবে? এবং এছাড়াও, আমি Stringটাইপটি কীভাবে সংজ্ঞায়িত করব ?
ক্রিশ্চিয়ান ডিন 21

1
@ মিঃ পাইথন সরলতম ক্ষেত্রে, এটি কেবলমাত্র অক্ষরের স্ট্রিং যা লেজিকাল উত্পাদনের সাথে মেলে। সুতরাং, আপনি যদি foo (23, "বার") দেখতে পান তবে আপনি টোকেনগুলি [আইডি, "ফু"], [লারপেন, "("), [নম্বর, "23"], [কোমা, "," পেয়ে যাবেন ], [STRING, "" 23 ""], [আরপিআরএন, ")"] । তথ্য সংরক্ষণ করা গুরুত্বপূর্ণ হতে পারে। অথবা আপনি অন্য কোনও পদ্ধতি অবলম্বন করতে পারেন এবং মানটির একটি ইউনিয়ন টাইপ থাকতে পারে যা স্ট্রিং বা একটি সংখ্যা ইত্যাদি হতে পারে এবং আপনি কী ধরণের টোকেন টাইপের উপর ভিত্তি করে সঠিক মানের প্রকারটি বেছে নিতে পারেন (উদাহরণস্বরূপ, টোকেন টাইপটি যখন NUMBER হয়) , value.num ব্যবহার করুন, এবং এটি যখন STRING, মান ব্যবহার করুন str
জোশুয়া টেলর 21

@ এমপিপিথন "এবং এছাড়াও, আমি স্ট্রিংয়ের ধরণ কীভাবে সংজ্ঞায়িত করব?" আমি একটি জাভা-ইশ মানসিকতা থেকে লিখছিলাম। আপনি যদি সি ++ এ কাজ করছেন তবে আপনি সি ++ এর স্ট্রিং টাইপ ব্যবহার করতে পারেন, বা আপনি সিতে কাজ করছেন তবে আপনি একটি চর * ব্যবহার করতে পারেন। মোদ্দা কথাটি হ'ল একটি টোকেনের সাথে সম্পর্কিত, আপনার সাথে সংশ্লিষ্ট মান রয়েছে বা মানটি উত্পাদন করতে আপনি যে পাঠ্যটি ব্যাখ্যা করতে পারেন।
জোশুয়া টেলর 21 ই

1
@ ollydbg23 এটি একটি বিকল্প এবং অযৌক্তিক নয়, তবে এটি সিস্টেমকে অভ্যন্তরীণভাবে কম সুসংগত করে তোলে। উদাহরণস্বরূপ, আপনি যদি শেষের শহরটি পার্স করার জন্য স্ট্রিংয়ের মানটি চান তবে আপনাকে এখন স্পষ্টভাবে একটি নাল মানটি পরীক্ষা করতে হবে এবং তারপরে স্ট্রিংটি কী হবে তা সন্ধান করার জন্য একটি বিপরীত টোকেন টু-স্ট্রিং লকআপ ব্যবহার করতে হবে। এছাড়াও, এটি লেক্সার এবং পার্সারের মধ্যে শক্ত সংযুক্তি; আপডেট করার জন্য আরও কোড রয়েছে যদি LPAREN কখনও কখনও বিভিন্ন বা একাধিক স্ট্রিংয়ের সাথে মেলে।
জোশুয়া টেলর

2
@ ollydbg23 একটি ক্ষেত্রে সাধারণ ছদ্ম-মিনিফায়ার হতে পারে। এটি করা যথেষ্ট সহজ parse(inputStream).forEach(token -> print(token.string); print(' '))(যেমন, কেবলমাত্র টোকেনগুলির স্ট্রিং মানগুলি স্পেস দ্বারা পৃথক করে প্রিন্ট করুন)। এটা বেশ দ্রুত। এমনকি যদি LPAREN কেবল "(") থেকে আসে তবে এটি স্মৃতিতে একটি ধ্রুব স্ট্রিং হতে পারে, সুতরাং টোকনে এটির উল্লেখ সহ নাল রেফারেন্স অন্তর্ভুক্ত করার চেয়ে আর ব্যয়বহুল হতে পারে। সাধারণভাবে, আমি বরং লিখি write কোড যা আমাকে বিশেষ ক্ষেত্রে কোনও কোড করে না
জোশুয়া টেলর

6

শিরোনামে যেমন বলা হয়েছে, কোনও লেক্সারের পার্সারটি কোন ডেটা টাইপের ফিরতি / ফিরিয়ে দেওয়া উচিত?

"টোকেন", স্পষ্টতই। একজন lexer, টোকেন একটি স্ট্রিম উৎপন্ন তাই এটি একটি প্রবাহ ফেরত পাঠাবেন টোকেন

তিনি ইতিমধ্যে বিদ্যমান লেক্সার ফ্লেক্সের কথা উল্লেখ করেছিলেন এবং বলেছিলেন যে এর সাথে 'বিধি' লিখে লেখার হাত ধরে কোনও লেক্সার লেখার চেয়ে সহজ হবে।

মেশিন দ্বারা উত্পাদিত লেক্সারগুলির সুবিধা রয়েছে যে আপনি এগুলি দ্রুত তৈরি করতে পারেন যা বিশেষত সহজলভ্য যদি আপনি ভাবেন যে আপনার লেক্সিকাল ব্যাকরণটি অনেক পরিবর্তন করতে চলেছে। তাদের অসুবিধা রয়েছে যে আপনি প্রায়শই আপনার প্রয়োগের পছন্দগুলিতে খুব বেশি নমনীয়তা পান না।

বলেছিল, "সরল" হলে কে যত্ন করে? লেক্সার লেখা সাধারণত হার্ড অংশ হয় না!

কোনও লেক্সার লেখার সময় এবং ধরে নেওয়া যায় যে এটি কেবলমাত্র একটি ডেটা টাইপ (স্ট্রিং বা সংখ্যা) ফেরত দিতে পারে, এটি আরও যুক্তিযুক্ত পছন্দ হতে পারে?

আমরাও। কোনও লেসারের সাধারণত একটি "পরবর্তী" অপারেশন থাকে যা একটি টোকেন প্রদান করে, সুতরাং এটি একটি টোকেন ফিরিয়ে দেয় । একটি টোকেন একটি স্ট্রিং বা একটি সংখ্যা নয়। এটি একটি টোকেন।

আমি যে সর্বশেষ লেক্সারটি লিখেছিলাম তা হ'ল "সম্পূর্ণ বিশ্বস্ততা" লেক্সার, যার অর্থ এটি একটি টোকেন দিয়েছিল যা সমস্ত সাদা স্থান এবং মন্তব্যের অবস্থান - যা প্রোগ্রামকে আমরা "ট্রিভিয়া" বলি track ট্র্যাক করেছিলাম the আমার লেক্সারে একটি টোকেন হিসাবে সংজ্ঞায়িত হয়েছিল:

  • নেতৃস্থানীয় ট্রিভিয়ার একটি অ্যারে
  • একটি টোকেন ধরণের
  • অক্ষরগুলির একটি টোকেন প্রস্থ
  • ট্রেলিং ট্রিভিয়ার একটি অ্যারে

ট্রিভিয়া হিসাবে সংজ্ঞায়িত করা হয়েছিল:

  • একটি ট্রিভিয়া ধরণের - সাদা স্থান, নিউলাইন, মন্তব্য এবং আরও অনেক কিছু
  • অক্ষরগুলির মধ্যে একটি ট্রিভিয়া প্রস্থ

সুতরাং যদি আমরা কিছু ছিল

    foo + /* comment */
/* another comment */ bar;

টোকেন ধরণের সঙ্গে চার টোকেন হিসাবে লেক্স হবে Identifier, Plus, Identifier, Semicolon, এবং প্রস্থ 3, 1, 3, 1. প্রথম শনাক্তকারী নেতৃস্থানীয় গঠিত ট্রিভিয়ার হয়েছে Whitespace4 প্রস্থে এবং তুচ্ছ বস্তু trailing Whitespace1. প্রস্থ সঙ্গে Plusকোন নেতৃস্থানীয় ট্রিভিয়ার এবং একটি সাদা স্থান, একটি মন্তব্য এবং একটি নতুন লাইন সমন্বিত ট্রিভিয়া ট্রেলিং। চূড়ান্ত শনাক্তকারীটির একটি মন্তব্য এবং একটি স্থান ইত্যাদির একটি অগ্রণী ট্রিভিয়া রয়েছে।

এই স্কিমের সাহায্যে ফাইলের প্রতিটি অক্ষর লেক্সারের আউটপুট হিসাবে গণ্য হয়, যা সিনট্যাক্স রঙ করার মতো জিনিসগুলির একটি সহজ সম্পত্তি।

অবশ্যই, যদি আপনার ট্রিভিয়ার প্রয়োজন না হয় তবে আপনি কেবল একটি টোকেন দুটি জিনিস তৈরি করতে পারেন: ধরণ এবং প্রস্থ।

আপনি লক্ষ্য করতে পারেন যে টোকেন এবং ট্রিভিয়ায় কেবলমাত্র তাদের প্রস্থ রয়েছে, উত্স কোডে তাদের পরম অবস্থান নয়। ইচ্ছাকৃত। এই জাতীয় স্কিমের সুবিধা রয়েছে:

  • এটি মেমরি এবং তারের ফর্ম্যাটে কমপ্যাক্ট
  • এটি সম্পাদনাগুলিতে পুনরায় লেক্সিং সক্ষম করে; লেক্সার যদি কোনও আইডিইয়ের অভ্যন্তরে চলছে তবে এটি দরকারী useful এটি হ'ল, যদি আপনি কোনও টোকনে কোনও সম্পাদনা সনাক্ত করেন, আপনি সম্পাদনার আগে আপনার লেক্সারটিকে কয়েকটি টোকনে ব্যাকআপ দিন এবং আপনি আগের টোকেন স্ট্রিমের সাথে সিঙ্ক না হওয়া অবধি আবার লেক্সিং শুরু করবেন। যখন আপনি কোনও অক্ষর টাইপ করেন সেই অক্ষরের পরিবর্তনের পরে প্রতিটি টোকেনের অবস্থান হয়, তবে সাধারণত মাত্র এক বা দুটি টোকেন প্রস্থে পরিবর্তিত হয়, আপনি সেই সমস্ত অবস্থা পুনরায় ব্যবহার করতে পারবেন।
  • প্রতিটি টোকেনের সঠিক চরিত্রের অফসেটগুলি টোকন স্ট্রিমের উপরে পুনরাবৃত্তি করে এবং বর্তমান অফসেটের ট্র্যাক রেখে সহজেই নেওয়া যায়। একবার আপনার কাছে যথাযথ চরিত্রের অফসেট পরে প্রয়োজনীয় পাঠ্যটি উত্তোলন করা সহজ।

যদি আপনি এইরকম কোনও দৃশ্যের বিষয়ে চিন্তা না করেন তবে একটি টোকেনকে এক ধরণের এবং প্রস্থের পরিবর্তে এক ধরনের এবং অফসেট হিসাবে উপস্থাপন করা যেতে পারে।

তবে এখানে মূল গ্রহণযোগ্যতা হ'ল: প্রোগ্রামিং হ'ল দরকারী বিমূর্ততা তৈরি করার শিল্প । আপনি টোকেনগুলি চালিত করছেন, সুতরাং টোকেনগুলির উপর একটি দরকারী বিমূর্ততা তৈরি করুন এবং তারপরে আপনি কীভাবে প্রয়োগকরণের বিবরণ এটির অন্তর্গত তা নিজের জন্য বেছে নিতে পারেন।


3

সাধারণত, আপনি একটি ছোট কাঠামো ফিরে আসেন যার মধ্যে একটি সংখ্যা রয়েছে যা টোকেন (বা ব্যবহারের সহজলভ্যতার জন্য এনাম মান) এবং একটি alচ্ছিক মান (স্ট্রিং, বা সম্ভবত জেনেরিক / টেম্প্লেড মান)। আরেকটি পদ্ধতির অতিরিক্ত উপাদান বহন করা প্রয়োজন যে উপাদানগুলির জন্য একটি উত্পন্ন প্রকার ফিরে আসা হবে। উভয়ই হালকা বিরক্তিকর, তবে একটি ব্যবহারিক সমস্যার যথেষ্ট পরিমাণ সমাধান solutions


হালকা বিরক্তিকর বলতে কী বোঝ ? তারা স্ট্রিং মান পেতে অক্ষম উপায়?
ক্রিশ্চিয়ান ডিন 21

@ মিঃ পাইথন - কোডে ব্যবহারের আগে তারা প্রচুর পরিমাণে চেক নিয়ে যাবে, যা অদক্ষ, তবে মোরডো কোডটি আরও জটিল / ভঙ্গুর করে তোলে।
টেলাস্টিন

সি ++ তে কোনও লেক্সার ডিজাইন করার সময় আমার অনুরূপ প্রশ্ন রয়েছে, আমি কোনও Token *বা একটি সহজভাবে ফিরে আসতে পারি Token, বা TokenPtrযা Tokenক্লাসের একটি ভাগ করে নেওয়া পয়েন্টার । তবে আমি দেখতে পাচ্ছি যে কিছু লেক্সার কেবল একটি টোকেনটাইপ রিটার্ন করে এবং স্ট্রিং বা সংখ্যা মানটি অন্যান্য গ্লোবাল বা স্ট্যাটিক ভেরিয়েবলগুলিতে সঞ্চয় করে। আরেকটি প্রশ্ন হ'ল আমরা কীভাবে অবস্থানের তথ্য সংরক্ষণ করতে পারি, আমার কী টোকেন স্ট্রাকের টোকেনটাইপ, স্ট্রিং এবং অবস্থান ক্ষেত্র থাকতে হবে? ধন্যবাদ।
ollydbg23

@ ollydbg23 - এগুলির যে কোনও একটি কাজ করতে পারে। আমি একটি কাঠামো ব্যবহার করতে হবে। এবং অ-শিক্ষণীয় ভাষার জন্য আপনি যেভাবেই কোনও পার্সার জেনারেটর ব্যবহার করবেন।
তেলস্তিন

@ টেলাস্টিন জবাবের জন্য ধন্যবাদ। আপনার মানে টোকেন স্ট্রাক্ট এর মতো কিছু হতে পারে struct Token {TokenType id; std::string lexeme; int line; int column;}, তাই না? লেক্সারের কোনও সার্বজনীন ক্রিয়াকলাপের জন্য, যেমন PeekToken(), ফাংশনটি কোনও Token *বা ফিরে আসতে পারে TokenPtr। আমি মনে করি এটি কিছুক্ষণের জন্য, যদি ফাংশনটি কেবল টোকেনটাইপটি ফিরিয়ে দেয়, পার্সার কীভাবে টোকেন সম্পর্কিত অন্যান্য তথ্য পাওয়ার চেষ্টা করবেন? সুতরাং, এই জাতীয় ফাংশন থেকে ফিরে আসার জন্য ডেটাটাইপের মতো পয়েন্টার পছন্দ করা হয়। আমার ধারণা সম্পর্কে কোন মন্তব্য? ধন্যবাদ
ollydbg23
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.