ÃÑ ÆäÀÌÁö ¼ö : 3224
![]()
|
Facebook Joinc ±×·ì
Joinc QA »çÀÌÆ®
ÇöÀçÀ§Ä¡ : docbook>lex_yacc_howto
![]()
Tweet
joinc´Â Firefox¿Í chrome¿¡¼ Å×½ºÆ® Çß½À´Ï´Ù. IE¿¡¼´Â Å×À̺íÀÌ ±úÁö°Å³ª À̹ÌÁö°¡ º¸ÀÌÁö ¾ÊÀ» ¼ö ÀÖ½À´Ï´Ù. ƯÈ÷ ±¸±Û DocsÀ̹ÌÁöÀÇ °æ¿ì ¿¢¹Úó¸®µÉ ¼ö ÀÖ½À´Ï´Ù.
HTML º¯È¯¹®¼
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook V4.1//EN">
<article lang="ko">
<!-- -->
<!-- ¹®¼ Á¤º¸ -->
<!-- -->
<articleinfo>
<title>Flex and Bison Howto</title>
<author>
<surname>À±»ó¹è</surname>
<affiliation>
<address>
<email>www.joinc.co.kr</email>
</address>
</affiliation>
</author>
<revhistory>
<revision>
<revnumber>0.89</revnumber>
<date>2004³â 07¿ù 25ÀÏ 12½Ã</date>
<revremark>¿ÀŸ ¼öÁ¤</revremark>
</revision>
<revision>
<revnumber>0.88</revnumber>
<date>2004³â 07¿ù 25ÀÏ 04½Ã</date>
<revremark>°è»ê±â ¿¹Á¦ Ãß°¡</revremark>
</revision>
<revision>
<revnumber>0.85</revnumber>
<date>2004³â 07¿ù 22ÀÏ 09½Ã</date>
<revremark>¹ø¿ª¿¡¼ ¹®¼ Âü°í ½ºÅ¸ÀÏ º¯°æ</revremark>
</revision>
<revision>
<revnumber>0.82</revnumber>
<date>2004³â 07¿ù 21ÀÏ 09½Ã</date>
<revremark>lex/yacc¸¦ flex/bision ±â¹ÝÀ¸·Î º¯°æ, 4Àå Ãß°¡</revremark>
</revision>
<revision>
<revnumber>0.81</revnumber>
<date>2004³â 07¿ù 20ÀÏ 09½Ã</date>
<revremark>¹ø¿ª½ÃÀÛ 1-3Àå</revremark>
</revision>
<revision>
<revnumber>0.8</revnumber>
<date>2002³â 04¿ù 20ÀÏ 19½Ã</date>
<revremark>¿øº» ¹®¼ÀÛ¼º</revremark>
</revision>
</revhistory>
</articleinfo>
<!--
-->
<!-- ¼½¼Ç ½ÃÀÛ
-->
<!--
-->
<section>
<title>¼Ò°³</title>
<para>
¹®¼ÀÇ ¸¹Àº ºÎºÐÀº <ulink url="http://www.tldp.org/HOWTO/Lex-YACC-HOWTO.html">Lex, Yacc Howto</ulink>¿Í
<ulink url="http://epaperpress.com/lexandyacc/">Compact Guide to Lex & Yacc</ulink>¸¦ Âü°íÇϰí ÀÖ½À´Ï´Ù.
</para>
<para>
¸¸¾à ´ç½ÅÀÌ ¿À·£½Ã°£µ¿¾È À¯´Ð½º ȯ°æ¿¡¼ ÇÁ·Î±×·¡¹ÖÀ» ÇØ¿Ô´Ù¸é LEX¿Í YACC¶ó´Â
À̸§ÀÇ ´Ù¼Ò ½Åºñ½º·¯¿î ´À³¦À» ÁÖ´Â ÇÁ·Î±×·¥¿¡ ´ëÇØ¼ µé¾î ºÃÀ» °ÍÀÌ´Ù.
Ȥ ´ç½ÅÀÌ GNU/Linux¿¡ ´õ Ä£¼÷ÇÏ´Ù¸é Flex¿Í BisonÀ̶ó´Â ÇÁ·Î±×·¥¿¡ ´ëÇØ¼µµ
¸î¹ø Á¤µµ´Â µé¾î ºÃÀ» °ÍÀÌ´Ù. Flex´Â Vern Paxon¿¡ ÀÇÇØ¼ ¸¸µé¾îÁø LexÀÇ È®Àå
µµ±¸°ÝÀÎ ÇÁ·Î±×·¥À̸ç, BisonÀº YACCÀÇ GNU¹öÁ¯°ÝÀÎ ÇÁ·Î±×·¥ÀÌ´Ù. ¿©±â¿¡¼´Â
Lex¿Í YaccÀÇ È°®¾îÀüÀ̶ó°í ÇÒ¼ö ÀÖ´Â Bison°ú Flex¿¡ ´ëÇØ¼ ´Ù·ê °ÍÀÌ´Ù.
¿øÁ¶°ÝÀÎ Yacc¿Í Lex¿ÍÀÇ Â÷ÀÌÁ¡ÀÌ °ÅÀÇ ¾øÀ¸¹Ç·Î ȣȯ¿¡ ¹®Á¦°¡ »ý±âÁö´Â
¾ÊÀ» °ÍÀÌ´Ù.
¾î¶µç GNUȯ°æ¿¡¼ÀÇ °³¹ßÀº GNUÅøÀº Bison°ú flex°¡ Á»´õ ÀÚ¿¬½º·´´Ù.
</para>
<para>
À̵é ÇÁ·Î±×·¥Àº ´ç½ÅÀÌ ¸Å¿ì Áß¿äÇÏ°Ô »ç¿ëÇÏ´Â C ÄÄÆÄÀÏ·¯¿Í °°Àº ÇÁ·Î±×·¥ÀÇ
ÀÛ¼º¿¡ Áß¿äÇÏ°Ô »ç¿ëµÇ´Âµ¥, ±× Á߿伺¿¡ ºñÇØ¼ man ÆäÀÌÁö´Â ½â ÈǸ¢ÇÏÁö
¸øÇؼ À̰͸¸ À» °¡Áö°í´Â ÀÌµé µµ±¸¸¦ »ç¿ëÇÒ ¼ö°¡ ¾ø´Ù. ¿©±â¿¡¼´Â ÀÌµé µµ±¸¸¦
½ÇÁúÀûÀ¸·Î »ç¿ëÇÒ ¼ö ÀÖµµ·Ï Á»´õ ½Ç¿ëÀû °üÁ¡¿¡¼ ´Ù·ê °ÍÀÌ´Ù.
</para>
<section>
<title>ÀÌ ¹®¼¿¡¼ ÇÒ ¼ö ¾ø´Â °Í</title>
<para>
½ÃÁß¿¡´Â ÀÌ¹Ì ´Ù¾çÇÑ Á¾·ùÀÇ Lex¿Í Yacc¸¦ ÁÖÁ¦·Î Çϰí ÀÖ´Â ÁÁÀº Ã¥µéÀÌ
³ª¿Í ÀÖ´Ù.(¿ö³«¿¡³ª Flex/Bison°ú ºñ½ÁÇϱ⠶§¹®¿¡, Àúµé Ã¥À» °¡Áö°í
Flex¿Í BisonÀ» ÇнÀÇϱ⵵ ÇÑ´Ù.)
ºñ·Ï ÀÌ ¹®¼°¡ Bison°ú Flex¸¦ ÇнÀÇϴµ¥ ¸¹Àº µµ¿òÀ» ÁÖ±ä ÇϰÚÁö¸¸,
À̵é Ã¥º¸´Ù ´õ ³ºÀº Á¤º¸¸¦ Á¦°øÇØÁÖ±ä Èûµé °ÍÀÌ´Ù.
À̵é Ã¥Àº ´ëºÎºÐÀÇ °æ¿ì Ã¥ÀÓ°¨À» °¡Áö°í ÀÛ¼ºµÇ¾ú±â ¶§¹®¿¡ ÀÌ ¹®¼¿¡¼
Á¦½ÃÇÏÁö ¸øÇÑ ´Ù¸¥ Áß¿äÇÑ Á¤º¸µéÀ» °¡Áö°í ÀÖÀ» °ÍÀÌ´Ù.
ÀÌ ¹®¼´Â Flex¿Í BisonÀ» Á»´õ ½±°Ô Á¢ÇÒ ¼ö ÀÖ±â À§ÇÑ
ÀÔ¹®¼ Á¤µµ·Î Ȱ¿ëÀ» ÇØÁÖ±æ ¹Ù¶õ´Ù.
</para>
<para>
¶ÇÇÑ À̹®¼¸¦ ÀÛ¼ºÇÑ ÀúÀÚ´Â Flex/Bison Àü¹®°¡°¡ ¾Æ´Ï¸ç, °øºÎÇϸé¼
ÀÌ ¹®¼¸¦ ÀÛ¼ºÇß´Ù. ÀÌÁ¡À» ¿°µÎ¿¡ µÎ°í ÀÌ ¹®¼¸¦ Àб⠹ٶõ´Ù. ´ëºÎºÐÀÇ ¿¹Á¦µéÀº
µ¹¾Æ°¡´ÂÁö È®ÀÎÇϱâ À§ÇÑ °£´ÜÇÑ ¼öÁØ¿¡¼ ÀÛ¼ºµÉ °ÍÀÌ´Ù. Á»´õ Çö½Ç°¨ ÀÖ´Â ¿¹Á¦¸¦
Ãß°¡ÇÏ±æ ¿øÇÑ
´Ù¸é ¾ðÁ¦µçÁö ÀÌ ¹®¼ÀÇ ¿øº»À» ¼öÁ¤ÇÏ´Â Á¤µµ·Î Âü°¡ÇÒ ¼ö ÀÖÀ» °ÍÀÌ´Ù.
</para>
</section>
<section>
<title>¹®¼ÀÇ ´Ù¿î·Îµå</title>
<para>
</para>
</section>
<section>
<title>Flex¿Í Bison</title>
<para>
ÇÊÀÚ°¡ ÇÑ»ìÀÌ´ø 1975³â°æ ¹«·Æ ÄÄÆÄÀÏ·¯¸¦ ÀÛ¼ºÇÏ´Â °ÍÀº »ç¶÷ÀÇ ¾Ö°£ÀåÀ»
³ìÀÌ´Â Àΰ£ÀÇ Àγ»·ÂÀÌ ¾îµð±îÁöÀΰ¡¸¦ Å×½ºÆ®ÇÏ´Â °íµµÀÇ ÂüÀ»¼º°ú ÁýÁß·ÂÀ»
ÇÊ¿ä·Î ÇÏ´Â ÀÛ¾÷À̾ú´Ù. ÀÌ·¯ÇÑ ÀÏ·ÃÀÇ ÀÛ¾÷À» Á»´õ ½±°Ô ÇϱâÀ§Çؼ
Johnson°ú Lesk¶õ »ç¶÷µéÀÌ lex¿Í yacc¶ó´Â µµ±¸¸¦ ¸¸µé°Ô µÇ¾ú´Ù. ÀÌ µµ±¸´Â
ÄÄÆÄÀÏ·¯ÀÇ ÀÛ¼ºÀ» ¸Å¿ì °£´ÜÇÏ°Ô Ã³¸®ÇÒ ¼ö ÀÖ´Â ÈǸ¢ÇÑ ±â´ÉÀ» °¡Áö°í ÀÖ¾úÀ¸¸ç
°è¼Ó ¹ßÀüÀ» ÇØ¼ 1986³â°æ Áö±Ý ¿ì¸®°¡ »ç¿ëÇÏ´Â Çö´ëÀûÀÎ ±â´ÉÀ» °¡Áø
lex¿Í yacc°¡ ¹ßÇ¥µÇ°Ô µÇ¾ú´Ù. lex¿Í yacc´Â ¸Å¿ì ÈǸ¢ÇÑ µµ±¸ ¿´±â ¶§¹®¿¡
¾Æ·¡¿Í °°Àº ´Ù¸¥ ¸¹Àº ¹öÁ¯µéÀÌ ¸¸µé¾îÁö°Ô µÇ¾ú´Ù.
<orderedlist>
<listitem>
<para>
Mortice Kern Systems(MKS), http://www.mks.com
</para>
</listitem>
<listitem>
<para>
(¿ì¸®°¡ ´Ù·ç°íÀÚ ÇÏ´Â)GNU flex, bison
</para>
</listitem>
<listitem>
<para>
Ming, http://www.mingw.org
</para>
</listitem>
<listitem>
<para>
¶Ç´Ù¸¥ lex, yacc¹öÁ¯, http://www.epaperpress.com
</para>
</listitem>
</orderedlist>
ÀÌÁß ÁÖ¸ñÇÒ ¸¸ÇѰÍÀ¸·Î´Â ³ôÀº ǰÁúÀ» Á¦°øÇÏ´Â »ó¿ëÁ¦Ç°ÀÎ MKS¿Í
GNU¶óÀ̼¾½ºÇÏ¿¡¼ ¹èÆ÷µÇ´Â flex,bisonÀÌ´Ù. flex, bisonÀº ÇöÀç ¹öÀü 1.24Àε¥,
»ó¿ëÀ¸·Îµµ °áÄÚ ¼Õ»ö¾ø´Â ±â´ÉÀ» Á¦°øÇϰí ÀÖ´Ù. Ming¿Í CygwinÀº À©µµ¿ì
½Ã½ºÅÛ¿¡¼ GNU¼ÒÇÁÆ®¿þ¾î¸¦ Æ÷ÆÃÇϱâ À§Çؼ »ç¿ëµÈ´Ù. ¿©±â¿¡´Â gcc¿Í g++°°Àº
ÄÄÆÄÀÏ·¯°¡ Æ÷ÇԵǾî ÀÖÀ¸¸ç »ó´çÇÑ ¼öÁØÀÇ GNU°³¹ß ȯ°æÀ» Á¦°øÇÑ´Ù.
</para>
<para>
¿©±â¿¡¼´Â lex¿Í yaccÀÇ ¿ø¸®¿¡ ´ëÇØ °£´ÜÇÏ°Ô ¼Ò°³Çϵµ·Ï ÇÒ °ÍÀÌ´Ù.
¿ì¸®ÀÇ ¸ñÀûÀÌ Flex¿Í BisonÀÇ »ç¿ë¹æ¹ýÀ̱ä ÇÏÁö¸¸ ¿ö³«¿¡ lex¿Í yaccÀÇ
¿ª»çÀû Àǹ̰¡ ±íÀº °ü°è·Î lex, yacc¸¦ ±âÁØÀ¸·Î Çß´Ù. ±×·¯³ª µµ±¸ÀÇ À̸§ÀÌ
Ʋ¸®°í ¸¸µé¾î³»´Â ÆÄÀÏÀÇ À̸§ÀÌ Æ²¸° ¿Ü¿¡´Â µ¿ÀÏÇÔÀ¸·Î ¹®Á¦µÉ°Ç ¾øÀ»
°ÍÀÌ´Ù.
</para>
<para>
lex´Â ¾îÈֺм®°ú scanner¸¦ À§ÇÑ CÄڵ带 »ý¼ºÇÑ´Ù. lex´Â ÀÔ·ÂµÈ ¹®ÀÚ¿¡¼
¸ÅĪµÇ´Â ¹®ÀÚ¿ÀÇ ÆÐÅÏÀ» ÀÌ¿ëÇØ¼ ¹®ÀÚ¿À» ÅäÅ«À¸·Î º¯È¯ÇÑ´Ù. ÅäÅ«Àº
¹®¹ýÀûÀ¸·Î ´õÀÌ»ó ³ª´ ¼ö ¾ø´Â ±âº»ÀûÀÎ ¾ð¾î ¿ä¼Ò¸¦ ¸»ÇÑ´Ù.
´ÙÀ½Àº ÄÄÆÄÀÏÀÌ ÀÌ·ç¾îÁö´Â ÀϹÝÀûÀÎ °úÁ¤ÀÌ´Ù. ÅäÅ«À» ¸¸µé¾î³»´Â °úÁ¤À»
ÁÖÀÇ ±í°Ô º¸±â ¹Ù¶õ´Ù.
</para>
<para>
½Éº¼ Å×À̺íÀ» ÀÌ¿ëÇØ¼ lex´Â ÀԷµǴ ¹®ÀÚ¿ÀÇ Æ¯Â¡À» °¡Á®¿Â´Ù.
½Éº¼ Å×À̺íÀº ¹®ÀÚ¿ÀÌ ¼ýÀÚÀÎÁö ´Ü¾îÀÎÁö¿Í °°Àº ŸÀÔ¿¡ ´ëÇÑ Á¤º¸¿Í
¾î¶² º¯¼ö¸¦ ÅëÇØ ¸Þ¸ð¸®¿¡ Á¢±ÙÇÒ ¼ö ÀÖÀ» °ÍÀÎÁö µîÀ» Á¤ÀÇ ÇÑ´Ù.
</para>
<para>
<figure id="pic1">
<title>ÄÄÆÄÀÏ °úÁ¤</title>
<graphic fileref="http://www.joinc.co.kr/albums/album01/ajv.png">
</figure>
Yacc´Â ±¸¹®ºÐ¼®°ú ÆÄ¼¸¦ À§ÇÑ CÄڵ带 »ý¼ºÇÑ´Ù. yacc´Â lex·Î ºÎÅÍ
ÅäÅ«À» ¹Þ¾ÆµéÀ̰í À̰ÍÀ» ¹®¹ý·ê¿¡ ³Ö°í µ¹·Á¼ ±¸¹®Æ®¸®(syntax tree)¸¦
»ý¼ºÇÑ´Ù. ±¸¹®Æ®¸®´Â ÅäÅ«±¸Á¶Ã¼ÀÇÀÇ °èÃþÀûÀÎ ±¸Á¶¸¦ ¸¸µé°Ô µÈ´Ù.
À§ÀÇ ±×¸²À» º¸¸é ¿¬»êÀÚ¿Í °ª¿¡ µû¶ó °èÃþ ±¸Á¶¸¦ º¼ ¼ö ÀÖÀ» °ÍÀÌ´Ù.
´ÙÀ½ ´Ü°è¿¡¼ Äڵ带 »ý¼º(code generator)ÇÏ°Ô µÈ´Ù. ÄÚµå »ý¼ºÀº
±íÀÌ ¿ì¼±À¸·Î ÀÌ·ç¾îÁö°Ô µÈ´Ù. ¸¸µé¾îÁö´Â ÄÚµå´Â ½Ã½ºÅÛÀÇ ¾î¼Àºí·¯°¡
ÇØ¼®°¡´ÉÇÑ ¾î¼Àºí¸®ÄÚµå ȤÀº ±â°è¾î Äڵ尡 µÈ´Ù.
</para>
<para>
<figure>
<title>lex¿Í yacc·Î ºÎÅÍ ÄÄÆÄÀÏ·¯¸¦ ÀÛ¼ºÇÏ´Â °úÁ¤</title>
<graphic fileref="http://www.joinc.co.kr/albums/album01/ajw.png">
</figure>
À§ÀÇ ±×¸²Àº lex¿Í yacc¿¡ ÀÇÇØ¼ »ç¿ëµÇ´Â ÆÄÀÏ À̸§ÀÇ ±ÔÄ¢ÀÌ´Ù.
¿¹¸¦ µé¾î BASIC ÄÄÆÄÀÏ·¯¸¦ ¸¸µç´Ù°í °¡Á¤ÇØ º¸ÀÚ. ¸ÕÀú ¿ì¸®´Â ÆÐÅϸÅĪ
±ÔÄ¢À» °¡Áø bas.i¶ó´Â lexÆÄÀÏÀ» ¸¸µé °ÍÀÌ´Ù. ±×¸®°í ¹®¹ý±ÔÄ¢À»
À§Çؼ basy.y¶ó´Â yaccÆÄÀÏÀ» ¸¸µé °ÍÀÌ´Ù. ±×¸®°í ¸¶Áö¸·À¸·Î gcc¸¦
ÀÌ¿ëÇØ¼ basc ¶ó´Â ÄÄÆÄÀÏ·¯¸¦ ¸¸µé°Ô µÈ´Ù.
<screen>
yacc -d bas.y # create y.tab.h, y.tab.c
lex bas.l # create lex.yy.c
gcc lex.yy.c y.tab.c -o basc # compile/link
</screen>
yacc´Â bas.y·Î ºÎÅÍ ¹®¹ý ±ÔÄ¢À» Àо°í ÆÄ¼¸¦ »ý¼ºÇÑ´Ù. ÆÄ¼ÀÇ À̸§Àº
y.tab.cÀε¥ ¿©±â¿¡´Â <emphasis>yyparse</emphasis>¶ó´Â ÇÔ¼ö¸¦ °¡Áö°í ÀÖ´Ù.
-d ¿É¼ÇÀº ÅäÅ«¿¡ ´ëÇÑ °¢Á¾ ¼±¾ðÀ» °¡Áø Çì´õÆÄÀÏÀÎ y.tab.h¸¦ »ý¼º½Ã۱â
À§Çؼ ÇÊ¿äÇÑ ¿É¼ÇÀÌ´Ù. ÀÌ Çì´õÆÛÀÏÀº lex¿¡¼ yacc¸¦ ¿¬°áÇϱâ À§Çؼ
»ç¿ëµÈ´Ù. lex´Â ¾îÈֺм®±â¿ªÇÒÀ» ÇÏ´Â <emphasis>yylex</emphasis>ÇÔ¼ö¸¦
Æ÷ÇÔÇÏ´Â <emphasis>lex.yy.c</emphasis> ÆÄÀÏÀ» »ý¼ºÇÑ´Ù.
</para>
<para>
¸¶Áö¸·À¸·Î gcc¿¡ ÀÇÇØ¼ lexer¿Í parserÀÌ ÄÄÆÄÀÏ µÈÈÄ ¸µÅ©µÇ¾î¼
<emphasis>basc</emphasis>½ÇÇàÆÄÀÏÀ» ¸¸µé°Ô µÈ´Ù. ÀÛ¼ºµÈ ÄÄÆÄÀÏ·¯¸¦
½ÇÇà ½Ã۸é mainÇÔ¼ö¿¡¼ yyparse¸¦ È£ÃâÇϰí yyparse´Â ÀÚµ¿ÀûÀ¸·Î yylex¸¦
È£ÃâÇØ¼ ÅäÅ«À» ¾ò¾î³½´Ù.
</para>
</section>
</section>
<section>
<title>Flex</title>
<para>
FlexÀÇ ¿øÁ¶´Â Lex·Î ÈçÈ÷ Lex generate¶ó°í Çϸç 'Lexer'¶ó°í ºÎ¸£±âµµ ÇÑ´Ù.
GNU¹öÁ¯Àº ¿©±â¿¡ F(Fast)¸¦ ºÙ¿©¼ ÀÌÀü ¹öÁ¯ÀÇ Lex¿Í ±¸ºÐÇϰí ÀÖ´Ù.
ÁÖ·Î ¹®ÀÚ¿À» ¹Þ¾ÆµéÀÌ°í ¹®ÀÚ¿Áß¿¡¼ ¿øÇÏ´Â Çü½ÄÀÇ ¹®ÀÚÀÇ Á¶ÇÕÀÌ ÀÖ´ÂÁö
È®ÀÎÇØ¼ ¾î¶² ÇÔ¼ö(ÀÛ¾÷)¸¦ ½ÇÇà½ÃŰ´Â ÀÏÀ» ÇÑ´Ù. ´ÙÀ½Àº °£´ÜÇÑ ¿¹Á¦ÀÌ´Ù.
<screen>
%{
#include <stdio.h>
%}
%%
stop printf("Stop command receive\n");
start printf("Start command receive\n");
%%
</screen>
ù¹øÂ° ¼½¼ÇÀ» º¸¸é %{¿Í %}¸¦ ÇѽÖÀ¸·Î ÇÏ°í ±× ¾È¿¡ include°¡ µé¾î°¡
ÀÖ´Â °ÍÀ» È®ÀÎÇÒ ¼ö ÀÖ´Ù. À̰ÍÀº ³ªÁß¿¡ »ç¿ëµÉ printf(3)ÇÔ¼ö¸¦ À§Çؼ
»ç¿ëµÈ´Ù. ¾Æ½Ã´Ù ½ÃÇÇ printfÇÔ¼ö´Â stdio.h¿¡ ¼±¾ðµÇ¾î ÀÖ´Ù.
</para>
<para>
´ÙÀ½ ¼½¼ÇÀº %%¸¦ ±¸ºÐÀÚ·Î ÇØ¼ ½ÃÀ۵Ǵµ¥, ù¹øÂ°´Â 'stop'À̶ó´Â ¹®ÀÚ¿À»
Ű·Î ½ÃÀÛÇϰí ÀÖ´Ù. À̰ÍÀº ¹®ÀÚ¿ÀÇ ÀÔ·ÂÁß¿¡ 'stop'¹®ÀÚ¿À» ´ë¸éÇÒ °æ¿ì
µÚ¿¡ ÀÖ´Â printf()¸¦ ½ÇÇàÇ϶ó´Â Àǹ̸¦ °¡Áø´Ù.
</para>
<para>
stop°ú ¸¶Âù°¡Áö·Î 'start'¿¡ ´ëÇØ¼µµ printf()¹®À» ½ÇÇàÇ϶ó°í ¼±¾ðµÇ¾î ÀÖ´Ù.
</para>
<para>
À§ÀÇ ¹®¹ýÀº lex¿¡¼ »ç¿ëµÉ ¼ö ÀÖ´Â ¹®¹ýÀ¸·Î, ÀÌ°É ½ÇÁ¦ »ç¿ëÇϱâ À§Çؼ´Â
C°¡ ÀνÄÇÒ ¼ö ÀÖ´Â ¹®¹ýÀ¸·Î º¯°æ½ÃÄÑÁà¾ß ÇÑ´Ù. ÀÌ·¯ÇÑÀÏ ¿ª½Ã lex°¡ ´ã´çÇÑ´Ù.
ÀÏÁ¾ÀÇ ¼±Ã³¸®±â ¶ó°í ÇÒ ¼ö ÀÖ´Ù.
<screen>
# flex example1.l
# gcc lex.yy.c -o example1 -lfl
</screen>
<note>
<para>
¸¸¾à flex´ë½Å¿¡ lex¸¦ »ç¿ëÇÏ±æ ¿øÇÑ´Ù¸é -lfl ´ë½Å -llÀ» »ç¿ëÇÏ¸é µÈ´Ù.
</para>
</note>
ÀÌÁ¦ example1¶ó´Â ½ÇÇàÆÄÀÏÀÌ »ý¼ºµÉ °ÍÀÌ´Ù. ÀÌ ÆÄÀÏÀ» ½ÇÇà½Ã۸é Ç¥ÁØÀÔ·ÂÀ»
¹Þ¾ÆµéÀ̴µ¥, stop/start¿Í °°Àº ¹®ÀÚ¿À» ¸¸³µÀ» ¶§ lex¹®¿¡¼ Á¤ÀÇÇÑ printf()
¹®À» ½ÇÇà½ÃŰ´Â°É È®ÀÎÇÒ ¼ö ÀÖÀ» °ÍÀÌ´Ù. ÀÔ·ÂÀ» Áß´ÜÇÏ°í ½ÍÀ» ¶§´Â (^D)¸¦
ÀÔ·ÂÇϵµ·Ï ÇÑ´Ù.
<screen>
# ./example1
start program
Start command receive
program
stopped
Stop command receive
ped
^D
</screen>
</para>
<section>
<title>Á¤±ÔÇ¥ÇöÀ» ÀÌ¿ëÇÑ ¸ÅĪ</title>
<para>
À̹ø ¿¹Á¦´Â ¾Æ¸¶µµ ¸Å¿ì À¯¿ëÇÏ°Ô ÀÀ¿ëÇÒ ¼ö ÀÖ´Â ¿¹Á¦·Î lex¿¡¼ÀÇ Á¤±ÔÇ¥Çö
Áö¿ø¿¡ ´ëÇÑ ¹æ¹ýÀ» ´ã°í ÀÖ´Ù.
<screen>
%{
#include <stdio.h>
%}
%%
[0123456789]+ printf("NUMBER\n");
[a-zA-Z][a-zA-Z0-9]* printf("WORD\n");
%%
</screen>
ÀÌ Lex ÆÄÀÏÀº "¹®ÀÚ¿(WORD)"¿Í "¼ýÀÚ"(NUMBER) 2Á¾·ù¿¡ ´ëÇÑ ¸ÅĪ Á¤º¸¸¦
°¡Áö°í ÀÖ´Ù. ÀϹÝÀûÀ¸·Î ÀÌ·¯ÇÑ °Ë»ç¸¦ (¼ÒÀ§¸»ÇÏ´Â)¼ÕÄÚµùÀ¸·Î ±¸ÇöÇÒ·Á°í
ÇÏ¸é »ó´çÈ÷ ±ÍÂúÀº ÀÛ¾÷ÀÌ ÇÊ¿äÇϰÚÁö¸¸ ¿©±â¿¡¼´Â À¯´Ð½º¿¡¼ ÀϹÝÀûÀ¸·Î
»ç¿ëÇÏ´Â Á¤±ÔÇ¥ÇöÆÐÅÏÀ» ÀÌ¿ëÇØ¼ °£´ÜÇÏ°Ô Ã³¸®ÇϰíÀÖ´Ù. Lex´Â ¼ýÀÚ¿¡
´ëÇÑ ¸ÅĪÀ» °Ë»çÇϱâ À§Çؼ ´ÙÀ½°ú °°Àº Á¤±ÔÇ¥Çö½ÄÀ» »ç¿ëÇϰí ÀÖ´Ù.
<screen>
[0123456789]+
</screen>
À̰ÍÀº 0123456789ÀÇ ±×·ì¿¡ ´ëÇØ¼ ÇϳªÀÌ»óÀÌ ¹ß°ßµÇ¾úÀ» ¶§ ¸¸Á·½Ã۶ó´Â
Àǹ̷Π´ÙÀ½°ú °°ÀÌ ´Ü¼øÇÏ°Ô Ç¥ÇöÇÒ ¼öµµ ÀÖ´Ù.
<screen>
[0-9]+
</screen>
¹®ÀÚ¿¡ ´ëÇÑ ¸ÅĪÀ» À§ÇÑ Á¤±ÔÇ¥Çö½ÄÀº ´ÙÀ½°ú °°ÀÌ »ç¿ëÇÒ ¼ö ÀÖ´Ù.
<screen>
[a-zA-Z][a-zA-Z0-9]*
</screen>
ù¹øÂ° ºÎºÐÀº 'a'¿¡¼ 'z'¼Ò¹®ÀÚ ÇϳªÈ¤Àº 'A'¿¡¼ 'Z'±îÁöÀÇ ¹®ÀÚÁï ¸ðµç
¿µ¹® ¾ËÆÄºª ´Ü¾î¸¦ ¶æÇÑ´Ù. µÎ¹øÂ° ºÎºÐÀº ¸ðµç¿µ¹®ÀÚ¿Í ¼ýÀÚ±îÁö¸¦
¶æÇÑ´Ù. ¸¶Áö¸·ÀÇ º°Ç¥("*")´Â 0°³ ÀÌ»óÀÇ ¹ß°ßÀ» ¶æÇÑ´Ù.
°á·ÐÀûÀ¸·Î ÇϳªÀÌ»óÀÇ ¿µ¹®°ú ¼ýÀÚ·Î ±¸¼ºµÈ ´Ü¾îµéÁß ¿¡¼ óÀ½ ù±ÛÀÚ°¡
¿µ¹®À¸·Î ½ÃÀÛÇÏ´Â ´Ü¾î¸¦ "¹®ÀÚ¿"·Î º¸°í ¸ÅĪÀ» ½ÃŰ°Ú´Ù´Â Àǹ̰¡ µÈ´Ù.
</para>
<para>
À§ÀÇ Á¤±ÔÇ¥Çö¿¡¼ "+"¿Í "*"ÀÇ Â÷À̸¦ ºÐ¸íÈ÷ ÇØµÑÇʿ䰡 ÀÖ´Ù. "+"´Â
Çϳª ÀÌ»ó ¹ß°ßµÇ¾î¾ß ÇÏ´Â°É ÀǹÌÇϸç, "*"´Â 0°³ ÀÌ»ó ¹ß°ßµÇ¾î¾ß ÇÔÀ»
ÀǹÌÇÑ´Ù.
</para>
<para>
À§ LexÆÄÀÏÀ» example2.l·Î ÀúÀåÇÑ´ÙÀ½ ÄÄÆÄÀÏÇØ¼ ½ÇÇà½ÃÄÑ º¸ÀÚ.
<screen>
# ./example1
foo
WORD
bar
WORD
123
NUMBER
bar123
WORD
123bar
NUMBER
WORD
</screen>
ÀÔ·ÂÁß¿¡ °ø¹é¹®ÀÚ(½ºÆäÀ̽º¹Ù)¸¦ Æ÷ÇÔ½ÃŰ¸é °ø¹é¹®ÀÚ´Â ±×´ë·Î Ãâ·ÂµÊÀ»
¾Ë ¼ö ÀÖ´Ù. ÀÌÀ¯´Â ¸ðµç whitespace´Â ¾î¶² °Í°úµµ ¸ÅνÃŰÁö ¾Ê±â ¶§¹®ÀÌ´Ù.
ÀÌµé ¹®ÀÚ´Â ´Ü¼ø Ãâ·Â½ÃŲ´Ù.
</para>
<para>
Flex¸¦ Á¦´ë·Î ´Ù·ç±â À§Çؼ´Â Á¤±ÔÇ¥Çö¿¡ ´ëÇÑ ¾î´ÀÁ¤µµÀÇ Áö½ÄÀ» °¡Áö°í
ÀÖ¾î¾ßÇÑ´Ù. Á¤±ÔÇ¥ÇöÀ» È¿°úÀûÀ¸·Î ÀÍÈ÷´Â °¡Àå ÁÁÀº ¹æ¹ýÀº Perl ¾ð¾î¸¦
ÀÌ¿ëÇØ¼ Á¤±ÔÇ¥Çö °ü·Ã ÇÁ·Î±×·¥À» ¸¸µé¾î º¸´Â°Ô µÉ°ÍÀÌ´Ù. ¶ÇÇÑ ½ÃÁßÀÇ
¸¹Àº Perl°ü·Ã Ã¥µéÀÌ »ó´çºÎºÐÀ» Á¤±ÔÇ¥Çö¿¡ ÇÒ¾ÖÇϰí ÀÖÀ¸¹Ç·Î À̵é Ã¥À»
±¸ÀÔÇØ¼ ÇнÀÇÏ´Â °Íµµ ÁÁÀº ¹æ¹ýÀÌ µÉ°ÍÀÌ´Ù.
</para>
<section>
<title>²À ÇÊ¿äÇÑ Á¤±ÔÇ¥Çö</title>
<para>
Á¤±ÔÇ¥ÇöÀº ¸Å¿ì ±¤¹üÀ§ÇÑ ÁÖÁ¦ÀÓÀ¸·Î ¿©±â¿¡¼´Â ¹Ýµå½Ã ÇÊ¿äÇÑ Á¤±ÔÇ¥Çö
±ÔÄ¢¿¡ ´ëÇØ¼¸¸ °£´ÜÈ÷ Á¤¸®Çϱâ·Î ÇϰڴÙ. Á¤±ÔÇ¥Çö¿¡ ´ëÇÑ ÀÚ¼¼ÇÑ Á¤º¸´Â
<ulink url="http://www.joinc.co.kr/modules/moniwiki/wiki.php/article_regex">Á¤±ÔÇ¥Çö</ulink>À»
Âü°íÇϱ⠹ٶõ´Ù.
<table>
<title>ÀÚÁÖ »ç¿ëµÇ´Â ÆÐÅϸÅĪ</title>
<tgroup cols=2>
<tbody>
<row>
<entry>.</entry>
<entry>°³Ç๮ÀÚ¸¦ Á¦¿ÜÇÑ ¸ðµç ¹®ÀÚ</entry>
</row>
<row>
<entry>\n</entry>
<entry>°³Ç๮ÀÚ</entry>
</row>
<row>
<entry>*</entry>
<entry>0ȤÀº ±× ÀÌ»óÀÇ ÀÏÄ¡</entry>
</row>
<row>
<entry>+</entry>
<entry>Çѹø ȤÀº ±× ÀÌ»óÀÇ ÀÏÄ¡</entry>
</row>
<row>
<entry>?</entry>
<entry>0ȤÀº ÇѹøÀÇ ÀÏÄ¡</entry>
</row>
<row>
<entry>^</entry>
<entry>¶óÀÎÀÇ Ã³À½¿¡¼ ÀÏÄ¡</entry>
</row>
<row>
<entry>$</entry>
<entry>¶óÀÎÀÇ ³¡¿¡¼ ÀÏÄ¡</entry>
</row>
<row>
<entry>a|b</entry>
<entry>a ¶Ç´Â b</entry>
</row>
<row>
<entry>(ab)+</entry>
<entry>ab¿Í ÇϳªÀÌ»ó ÀÏÄ¡</entry>
</row>
<row>
<entry>[]</entry>
<entry>¹®ÀÚ Å¬·¡½ºÀÇ ÁöÁ¤</entry>
</row>
</tbody>
</tgroup>
</table>
<table>
<title>ÆÐÅϹÌĪÀÇ »ç¿ë ¿¹</title>
<tgroup cols=2>
<tbody>
<row>
<entry>Ç¥Çö</entry>
<entry>¸ÅĪ</entry>
</row>
<row>
<entry>abc</entry>
<entry>abc</entry>
</row>
<row>
<entry>abc*</entry>
<entry>ab abc abcc abccc ...</entry>
</row>
<row>
<entry>a(bc)+</entry>
<entry>abc abcbc abcbcbc ...</entry>
</row>
<row>
<entry>a(bc)?</entry>
<entry>a abc</entry>
</row>
<row>
<entry>[abc]</entry>
<entry>a b c</entry>
</row>
<row>
<entry>[a-z]</entry>
<entry>a¿¡¼ z±îÁö</entry>
</row>
<row>
<entry>[a\-z]</entry>
<entry>a, -, z Áß Çϳª</entry>
</row>
<row>
<entry>[a\-z]</entry>
<entry>a, -, z Áß Çϳª</entry>
</row>
<row>
<entry>[-az]</entry>
<entry>-, a, z Áß Çϳª</entry>
</row>
<row>
<entry>[a-zA-Z0-9]+</entry>
<entry>ÇϳªÀÌ»óÀÇ ¸ðµç ¿µ¹®ÀÚ¿Í ¼ýÀÚ</entry>
</row>
<row>
<entry>[\t\n]+</entry>
<entry>whitespace ¹®ÀÚ</entry>
</row>
<row>
<entry>[^ab]</entry>
<entry>a¿Í b¸¦ Á¦¿ÜÇÑ ¸ðµç</entry>
</row>
<row>
<entry>[a^b]</entry>
<entry>a, ^, b Áß Çϳª</entry>
</row>
<row>
<entry>[a|b]</entry>
<entry>a, |, b Áß Çϳª</entry>
</row>
</tbody>
</tgroup>
</table>
flex¸¦ Á¦´ë·Î »ç¿ëÇϱâ À§Çؼ´Â À§ÀÇ Ç¥¿¡ Á¤¸®µÈ ÀÚÁÖ»ç¿ëµÇ´Â ÆÐÅϸÅĪÀÇ
³»¿ëµéÀº ±âº»ÀûÀ¸·Î ¼÷ÁöÇϰí ÀÖ¾î¾ß ÇÑ´Ù. µÎ¹øÂ° Ç¥¿¡ ÀÖ´Â°Ç ÆÐÅϸÅĪÀÇ
»ç¿ë¿¹ÀÌ´Ù.
</para>
</section>
</section>
<section>
<title>º¹ÀâÇÑ ¹®ÀåÀÇ ÆÄ½Ì</title>
<para>
À̹ø¿¡´Â ¾Æ·¡¿Í °°Àº Á»´õ º¹ÀâÇÑ ¹®ÀåÀ» ÆÄ½ÌÇØ º¸µµ·Ï ÇϰڴÙ.(bind¸¦ À§ÇÑ
¼³Á¤ÆÄÀÏÀÇ ÀϺκÐÀÌ´Ù)
<screen>
logging {
category lame-servers { null; };
category cname { null; };
};
zone "." {
type hint;
file "/etc/bind/db.root";
};
</screen>
</para>
<para>
Flex¹®À» È®½ÇÈ÷ ÀÛ¼ºÇϱâ À§Çؼ À§ÀÇ ºÐ¼®¹®ÀÚ¿¿¡¼ »ç¿ëµÇ°í ÀÖ´Â
ÅäÅ«µé¿¡ ´ëÇÑ Ä«Å×°í¸®¸¦ ¸¸µé Çʿ䰡 ÀÖ´Ù.
<itemizedlist>
<listitem>
<para>
'zone', 'type' °°Àº ¹®ÀÚ¿
</para>
</listitem>
<listitem>
<para>
'/etc/bind/db.root' °°Àº ÆÄÀÏÀ̸§
</para>
</listitem>
<listitem>
<para>
ÆÄÀÏÀ̸§À» °¨½Î´Âµ¥ »ç¿ëÇÏ´Â ÄõÅÍ(") ¹®ÀÚ
</para>
</listitem>
<listitem>
<para>
{, Áß°ýÈ£ ¿±â
</para>
</listitem>
<listitem>
<para>
}, Áß°ýÈ£ ´Ý±â
</para>
</listitem>
<listitem>
<para>
;, ¼¼¹ÌÄÝ·Ð
</para>
</listitem>
</itemizedlist>
</para>
<para>
´ÙÀ½Àº À§ÀÇ Ä«Å×°í¸®¸¦ ¸¸Á·½ÃŰ´Â LexÆÄÀÏÀÌ´Ù. ÆÄÀϸíÀº example3.l·Î
ÇÏÀÚ.
<screen>
%{
#include <stdio.h>
%}
%%
[a-zA-Z][a-zA-Z0-9]* printf("WORD ");
[a-zA-Z0-9\/.-]+ printf("FILENAME ");
\" printf("QUOTE ");
\{ printf("OBRACE ");
\} printf("EBRACE ");
; printf("SEMICOLON ");
\n printf("\n");
[ \t]+ /* ignore whitespace */;
%%
</screen>
À§ÀÇ lex ÆÄÀÏÀ» ÄÄÆÄÀÏÇѵڿ¡ Å×½ºÆ®Çغ¸¸é ´ÙÀ½°ú °°Àº °á°ú¸¦ È®ÀÎÇÒ ¼ö
ÀÖÀ» °ÍÀÌ´Ù.
<screen>
# ./example3 < test.txt
WORD OBRACE
WORD FILENAME OBRACE WORD SEMICOLON EBRACE SEMICOLON
WORD WORD OBRACE WORD SEMICOLON EBRACE SEMICOLON
EBRACE SEMICOLON
WORD QUOTE FILENAME QUOTE OBRACE
WORD WORD SEMICOLON
WORD QUOTE FILENAME QUOTE SEMICOLON
EBRACE SEMICOLON
</screen>
À§ÀÇ °á°ú¿¡¼ È®ÀÎÇÒ ¼ö ÀÖµíÀÌ ÀϹݼ³Á¤ÆÄÀÏ Çü½ÄÀ» °¡Áö´Â ²Ï º¹ÀâÇÑ
¹®Àåµµ ¾î·ÆÁö ¾Ê°Ô ÆÄ½ÌµÊÀ» ¾Ë ¼ö ÀÖ´Ù.
</para>
</section>
<section>
<title>flex¿¡ ¹Ì¸® Á¤ÀÇµÈ º¯¼öµé</title>
<para>
Áö±Ý±îÁöÀÇ ³»¿ëÀ» º¸¸é ¸î°³ flex¿¡¼ Á¤ÀÇÇØ¼ »ç¿ëÇÏ´Â º¯¼ö¿Í ÇÔ¼öµéÀÌ
º¸ÀÏ °ÍÀÌ´Ù. À̰͵éÀ» Ç¥·Î Á¤¸®ÇØ µÎ¾úÀ¸´Ï Âü°íÇϱ⠹ٶõ´Ù.
<table>
<title>flex¿¡¼ ¹Ì¸® Á¤ÀÇµÈ °ªµé</title>
<tgroup cols=2>
<tbody>
<row>
<entry>int yylex(void)</entry>
<entry>lexer¸¦ È£ÃâÇϰí ÅäÅ«À» ¸®ÅÏÇÑ´Ù.</entry>
</row>
<row>
<entry>char *yytext</entry>
<entry>¸ÅĪµÈ ¹®ÀÚ¿ÀÇ Æ÷ÀÎÅÍ</entry>
</row>
<row>
<entry>yyleng</entry>
<entry>¸ÅĪµÈ ¹®ÀÚ¿ÀÇ ±æÀÌ</entry>
</row>
<row>
<entry>yylval</entry>
<entry>ÅäÅ«¿¡ ´ëÇÑ Á¤º¸ °ª</entry>
</row>
<row>
<entry>int yywrap(void)</entry>
<entry></entry>
</row>
<row>
<entry>FILE *yyout</entry>
<entry>Ãâ·Â ÆÄÀÏ</entry>
</row>
<row>
<entry>FILE *yyin</entry>
<entry>ÀÔ·Â ÆÄÀÏ</entry>
</row>
<row>
<entry>INITIAL</entry>
<entry>initial start condition</entry>
</row>
<row>
<entry>BEGIN</entry>
<entry>condition switch start condition</entry>
</row>
<row>
<entry>ECHO</entry>
<entry>¸ÅĪµÈ ¹®ÀÚ¿À» ¾´´Ù.</entry>
</row>
</tbody>
</tgroup>
</table>
</para>
</section>
<section>
<title>Áö±Ý±îÁö ´Ù·é ³»¿ëµé</title>
<para>
Áö±Ý±îÁöÀÇ ³»¿ëµéÀ» ÅëÇÏ¿© Lex´Â ÀÓÀÇÀÇ ÀÔ·ÂÀ» ¹Þ¾Æµé¿©¼ °¢°¢ÀÇ ºÎºÐÀ»
Àǹ̸¦ °áÁ¤ÇÒ ¼ö ÀÖÀ½À» ¾Ë¾Ò´Ù. ÀÌ·¯ÇÑ °ÍÀ» 'Tokenizing'¶ó°í ÇÑ´Ù.
</para>
</section>
</section>
<section>
<title>Bison</title>
<para>
BisonÀÇ ¿øÁ¶°ÝÀÎ YACC¿¡ ´ëÇØ¼ ¸ÕÀú ¾Ë¾Æº¸±â·Î ÇÏÀÚ. YACC´Â
Yet Another Compiler CompilerÀÇ ¾àÀÚ·Î ÄÄÆÄÀÏ·¯¸¦ »ý¼ºÀ» À§ÇÑ ÇÁ·Î±×·¥
ÀÌ´Ù. compiler-generator ȤÀº compiler-compilerÀ̶ó°í ºÎ¸£±âµµ ÇÑ´Ù.
yacc´Â lex¿¡ ÀÇÇØ¼ ¾ò¾îÁø tokenµéÀÇ °ü°è¸¦ ±¸¼ºÇÏ´Â "±¸¹®ºÐ¼®±â"¸¦ »ý¼ºÇÏ´Â
ÅøÀÌ´Ù. yacc°¡ ³»ºÎÀûÀ¸·Î tokenÀ» ¾ò±â À§Çؼ lex¸¦ »ç¿ëÇϴµ¥,
lex¿Í yacc, flex¿Í bisonÀ» ÇÑ ¹À½À¸·Î ÇØ¼ ´Ù·ç´Â ÀÌÀ¯°¡ µÈ´Ù.
lex¸¦ È£ÃâÇϱ⠶§¹®¿¡ lexÀÇ »óÀ§¿¡ À§Ä¡ÇÏ°Ô µÈ´Ù. BisonÀº ÀÌ·¯ÇÑ ÀÏÀ» ÇÏ´Â
YACCÀÇ GNU¹öÁ¯À̸ç, ÇÏ´ÂÀÏ ¿É¼Çµî¿¡ ÀÖ¾î¼ °ÅÀÇ µ¿ÀÏÇÏ´Ù.
</para>
<para>
Bison(yacc)´Â BNF (Backus Naur Form)À» ÀÌ¿ëÇØ¼ ÇÊ¿äÇÑ ÀÏÀ» ¼öÇàÇÑ´Ù.
ÀÌ ±â¼úÀº John Backus ¿Í Peter Naur¿¡ ÀÇÇØ¼ ¸¸µé¾î Á³À¸¸ç ALGOL60 ¾ð¾î¸¦
Á¦ÀÛÇϴµ¥ »ç¿ëµÇ¾ú´Ù. BNF ¹®¹ýÀº ÀÚÀ¯·Î¿î ¹®¸Æ(context-free) ¾ð¾î¸¦
Ç¥ÇöÇϴµ¥ À¯¿ëÇÏ°Ô »ç¿ëÇÒ ¼ö ÀÖ´Ù. Çö´ëÀÇ ´ëºÎºÐÀÇ ÇÁ·Î±×·¡¹Ö ¾ð¾î´Â
BNF¸¦ ÀÌ¿ëÇØ¼ ¹®¸ÆÀ» Ç¥ÇöÇϰí ÀÖ´Ù.
</para>
<section>
<title>°£´ÜÇÑ ¿Âµµ Á¶Àý±â</title>
<para>
BisonÀÇ ¿ëµµ¸¦ È®ÀÎÇϱâ À§Çؼ °£´ÜÇÑ ¿Âµµ Á¶Àý±â¸¦ À§ÇÑ ¾ð¾î¸¦ ¸¸µå´Â
°úÁ¤À» ¿¹·Î µé¾î º¸°Ú´Ù. ¿Âµµ Á¶Àý±â¸¦ ¸¸µé±â À§Çؼ´Â ´ÙÀ½°ú °°ÀÌ
3°³ÀÇ ¼¼¼ÇÀÌ ÇÊ¿äÇÒ °ÍÀÌ´Ù.
<screen>
heat on
Heater on !
heat off
Heater off !
target temperature 22
New temperature set !
</screen>
À§¿¡¼ ¾òÀ» ¼ö ÀÖ´Â tokenÀº heat, on/off(»óÅÂ), target, temperature,
¼ýÀÚ(¿Âµµ ¼³Á¤¿ë) ÀÓÀ» ¾Ë ¼ö ÀÖ´Ù.
</para>
<para>
À§ÀÇ ÅäÅ«À» ºÐ¸®Çϱâ À§Çؼ ´ÙÀ½°ú °°Àº lex ÆÄÀÏÀ» ÀÛ¼ºÇϰí example4.l·Î
ÀúÀåÇϵµ·Ï ÇÑ´Ù.
<screen>
%{
#include <stdio.h>
#include "example4.tab.h"
%}
%%
[0-9]+ return NUMBER;
heat return TOKHEAT;
on|off return STATE;
target return TOKTARGET;
temperature return TOKTEMPERATURE;
\n /* ignore end of line */;
[ \t]+ /* ignore whitespace */;
%%
</screen>
À§ÀÇ Äڵ忡¼ ±âÁ¸°ú Å©°Ô ´Þ¶óÁø Á¡À» µÎ°¡Áö ¹ß°ßÇÒ ¼ö ÀÖÀ» °ÍÀÌ´Ù.
¿ì¼± example.tab.h ¶ó´Â ÆÄÀÏÀÌ ÀÎŬ·çµå µÇ¾î ÀÖ´Ù. ±×¸®°í printf()´ë½Å¿¡
tokenÀÇ À̸§À» ¸®ÅÏÇϰí ÀÖ´Ù. ÀÌ·¸°Ô ÅäÅ«ÀÇ °ªÀ» ¸®ÅÏÇÏ´Â ÀÌÀ¯´Â bisionÀÌ
tokenÀÇ Á¤º¸¸¦ ¹Þ¾Æ¼ À̸¦ ó¸®ÇÒ ¼ö ÀÖµµ·Ï Çϱâ À§ÇÔÀÌ´Ù.
example4.tab.h¿¡´Â °¢ token¿¡ ´ëÇØ¼ bisonÀÌ ¾î¶»°Ô ó¸®ÇØ¾ß ÇÒ°ÍÀÎÁö¿¡
´ëÇÑ Á¤º¸°¡ µé¾î°£´Ù.
</para>
<para>
bison ÄÚµå´Â Å©°Ô 3°¡Áö ºÎºÐÀ¸·Î ÀÌ·ç¾îÁø´Ù.
<screen>
... Á¤ÀÇ(definitions) ...
%%
... ±ÔÄ¢(rules) ...
%%
... ÇÔ¼öµé(subroutines) ...
</screen>
Á¤ÀÇ ºÎºÐ¿¡¼´Â ÅäÅ«°ú °¢Á¾ »ó¼ö¸¦ ¼±¾ðÇÑ´Ù. ±×¸®°í CÄڵ带
Æ÷ÇÔ½Ãų¼ö Àִµ¥, ÀÌ·²°æ¿ì %{¿Í %} »çÀÌ¿¡ ÇØ´ç CÄڵ带 Æ÷ÇÔ½ÃŰ¸é µÈ´Ù.
BNF ¹®¹ýÀº rule ¼½¼Ç¿¡ À§Ä¡Çϸç, ÇÔ¼ö ¼½¼Ç¿¡ »ç¿ëÀÚ Á¤ÀÇ ÇÔ¼ö¸¦ Ãß°¡½Ãų
¼ö ÀÖ´Ù.
</para>
<para>
example4.tab.h¿¡ ´ëÇØ¼ ¿ì¸®°¡ ½Å°æ¾µ ÇÊ¿ä´Â ¾ø´Ù. bison¹®¹ýÆÄÀÏÀ»
±ÔÄ¢´ë·Î ÀÛ¼ºÇØÁÖ°í³ª¼ bison¸¦ µ¹¸®¸é example4.tab.h´Â ÀÚµ¿ÀûÀ¸·Î »ý¼ºµÇ±â
¶§¹®ÀÌ´Ù. ´ÙÀ½Àº À§ÀÇ ÅäÅ«ÀÇ Á¤º¸¸¦ ó¸®ÇÒ ¼ö ÀÖµµ·Ï ÀÛ¼ºµÈ bison ¹®¹ý
ÆÄÀÏÀÌ´Ù.
<screen>
commands: /* empty */
| commands command
;
command:
heat_switch
|
target_set
;
heat_switch:
TOKHEAT STATE
{
printf("\tHeat turned on or off\n");
}
;
target_set:
TOKTARGET TOKTEMPERATURE NUMBER
{
printf("\tTemperature set\n");
}
;
</screen>
ù¹øÂ° ºÎºÐÀ» 'root'¶ó°í ºÎ¸£µµ·Ï ÇϰڴÙ. ¿©±â¿¡¼ ¿ì¸®´Â commands ¶ó´Â
·ê »ç¿ëÇßÀ¸¸ç, ±¸¼º¿ä¼Ò·Î command¸¦ °¡Áö°í ÀÖ´Ù.
</para>
<para>
µÎ¹øÂ° ·ê¿¡¼´Â command¿¡ ´ëÇØ¼ Á¤ÀÇÇϰí ÀÖ´Ù. ¿©±â¿¡¼´Â heat_switch¿Í
target_setµÎ°³ÀÇ ¸í·É¸¸À» Á¤ÀÇÇÑ´Ù. ÀÌµé ¸í·ÉÀ» ¼±¾ðÇϴµ¥
'|'ÀÌ »ç¿ëµÇ°í Àִµ¥, ÀÌ´Â command°¡ heat_switch ¶Ç´Â target_set¸¦
±¸¼º¿ä¼Ò·Î °¡Áö°í ÀÖÀ½À» ÀǹÌÇÑ´Ù.
</para>
<para>
heat_switch´Â HEAT token¿¡ ´ëÇÑ Ã³¸®¸¦ ´ã´çÇÏ´Â ±¸¼º¿ä¼Ò·Î 'heat'¿Í
state ÅäÅ«ÀÌ ¿Ã °æ¿ì À̸¦ ½ÇÇàÇϵµ·Ï Çß´Ù.
ÀÌ´Â È÷Å͸¦ ۰í ÄÓ¶§ 2°³ÀÇ ÅäÅ«À¸·Î ÀÌ·ç¾îÁö±â ¶§¹®ÀÌ´Ù.
</para>
<para>
¿Âµµ¸¦ ¼³Á¤ÇÏ´Â ¸í·ÉÀº 'target'°ú targetÀ¸·Î
ÁöÁ¤ÇÒ '°´Ã¼', ±×¸®°í '°ª'ÀÇ 3°³ÀÇ °´Ã¼·Î ÀÌ·ç¾îÁø´Ù. À̸¦ À§Çؼ
3°³ÀÇ ÅäÅ«ÀÌ ¸¸Á·ÇÒ ¶§ target_setÀÌ ½ÇÇàµÇµµ·Ï ·êÀ» ¸¸µé¾ú´Ù.
</para>
<section>
<title>¿ÏÀüÇÑ Bison ÆÄÀÏ</title>
<para>
´ÙÀ½Àº ÀÌ»óÀÇ ¸ðµç ³»¿ëÀ» Á¾ÇÕÇÑ Bison ÆÄÀÏÀÌ´Ù.
<screen>
%{
#include <stdio.h>
#include <string.h>
void yyerror(const char *str)
{
fprintf(stderr,"error: %s\n",str);
}
int yywrap()
{
return 1;
}
main()
{
yyparse();
}
%}
%token NUMBER TOKHEAT STATE TOKTARGET TOKTEMPERATURE
%%
commands: /* empty */
| commands command
;
command:
heat_switch
|
target_set
;
heat_switch:
TOKHEAT STATE
{
printf("\tHeat turned on or off\n");
}
;
target_set:
TOKTARGET TOKTEMPERATURE NUMBER
{
printf("\tTemperature set\n");
}
;
</screen>
yyerror()ÇÔ¼ö´Â Bison¿¡¼ ¿¡·¯¸¦ ¹ß°ßÇßÀ» ¶§, ¿¡·¯¸¦ µÇµ¹·ÁÁØ´Ù.
ÀÎÀÚ·Î ÁÖ¾îÁö´Â strÀ» Ãâ·ÂÇØ º½À¸·Î½á ¿ì¸®´Â °£´ÜÇÏ°Ô ¿¡·¯ÀÇ ³»¿ëÀ»
È®ÀÎÇÒ ¼ö ÀÖ´Ù.
</para>
<para>
yywrap()´Â ´Ù¸¥ ÆÄÀÏ·Î ºÎÅÍ °è¼ÓÀûÀ¸·Î Àб⸦ ¼öÇàÇϰíÀÚ ÇÒ¶§
»ç¿ëÇÑ´Ù.
</para>
<para>
mainÇÔ¼ö°¡ È£ÃâµÇ¾ú´Ù. mainÇÔ¼ö´Â ´ÜÁö yyparse¸¸À»
È£ÃâÇÏÁö¸¸ ¿ì¸®°¡ Áö±Ý±îÁö ¸¸µé¾ú´ø ·êÀ» ÀÌ¿ëÇØ¼ ÀԷµǴ ¹®ÀÚ¿À»
ÀÌ¿ëÇØ¼ ÀÛ¾÷À» ¼öÇàÇÑ´Ù.
</para>
<para>
¸¶Áö¸·À¸·Î ¿ì¸®°¡ »ç¿ëÇÏ°ÔµÉ ÅäÅ«À» ¼±¾ðÇÏ¿´´Ù. Áö±Ý±îÁöÀÇ
¸ðµç³»¿ëÀº yacc ¸¦ -d ¿É¼ÇÀ» ÁÖ°í ½ÇÇàÇÔÀ¸·Î½á, y.tab.h¿¡ ¾²¿©Áö°Ô
µÈ´Ù.
</para>
<para>
ÄÄÆÄÀÏÀº ¾Æ·¡¿Í °°ÀÌ ÀÌ·ç¾îÁø´Ù.
<screen>
# flex example4.l
# bison -d example4.y
# gcc lex.yy.c example4.tab.c -o example4
</screen>
ÀÌÁ¦ ¿ì¸®°¡ ¸¸µç ÇÁ·Î±×·¥ÀÌ Á¦´ë·Î ÀÛµ¿ÇÏ´ÂÁö Å×½ºÆ® ÇØº¸µµ·Ï ÇÏÀÚ.
<screen>
# ./example4
heat on
Heat turned on or off
heat off
Heat turned on or off
target temperature 10
Temperature set
target humidity 20
error: parse error
</screen>
¿ì¸®°¡ ¸¸µç ÇÁ·Î±×·¥Àº ±×·° Àú·° µ¹¾Æ°¡Áö¸¸ ¾ÆÁ÷ ¿Ïº®ÇÏÁö ¾ÊÀ½À»
¾Ë ¼ö ÀÖ´Ù. ´ÙÀ½Àý¿¡¼´Â Á»´õ ±×·²µíÇÏ°Ô ÀÛµ¿ÇÏ´Â ÇÁ·Î±×·¥À»
¸¸µé °ÍÀÌ´Ù.
</para>
</section>
</section>
<section>
<title>¿ÂµµÁ¶Àý ÇÁ·Î±×·¥ÀÇ ¾÷±×·¹À̵å</title>
<para>
¾î¶µç ¿ì¸®´Â ¹®ÀåÀ» ÆÄ½ÌÇØ¼ ¿øÇÏ´Â ·çƾÀ» ½ÇÇà°¡´ÉÇÑ ÇÁ·Î±×·¥À»
¸¸µé¾î ³Â´Ù. ±×·¯³ª Á»´õ ¿Ïº®ÇÏ°Ô ÀÛµ¿Çϱâ À§Çؼ´Â ´ÜÁö
"¹«¾ùÀ» ÆÄ½Ì Çß´Ù"°¡ ¾Æ´Ñ "ÆÄ½ÌÇÑ Á¤º¸°¡ ¹«¾ù"ÀÌ´Ù¶ó´Â °ªÀ» ¾ò¾î ¿Ã ¼ö
ÀÖ¾î¾ß ÇÑ´Ù. ¿¹¸¦ µéÀÚ¸é 'heat'´Â ¿ÂµµÁ¶Àý±â¸¦ ÄѰųª ²ô´Âµ¥, À̸¦
À§Çؼ´Â heat ÅäÅ« ´ÙÀ½ÀÇ 'on', 'off' ÅäÅ«À» °¡Á®¿Ã ¼ö ÀÖ¾î¾ß ÇÑ´Ù.
</para>
<para>
¶ÇÇÑ ¿Âµµ ¼³Á¤À» À§ÇÑ target temperatureÀÇ °æ¿ì ¿Âµµ °ªÀ» Àоî¿Ã ¼ö
ÀÖ¾î¾ß ÇÑ´Ù.
</para>
<para>
Flex´Â ¸ÅĪµÈ ´Ü¾îÀÇ ¹®ÀÚ¿À» 'yytex'¶ó´Â º¯¼ö¿¡ ÀúÀåÇÑ´Ù. ¶ÇÇÑ 'yylval'¿¡
¸®ÅϰªÀ» µÇµ¹·ÁÁÙ ¼öµµ ÀÖ´Ù. À̸¦ ÀÌ¿ëÇÏ¸é ÆÐÅϸÅĪÀÇ °á°ú¸¦ ³Ñ±æ ¼ö°¡
ÀÖ´Ù. ¾Æ·¡¿Í °°ÀÌ ÀÛ¼ºÇϰí example5.l ·Î ÀúÀåÇÏÀÚ.
<screen>
%{
#include <stdio.h>
#include "y.tab.h"
%}
%%
[0-9]+ yylval=atoi(yytext); return NUMBER;
heat return TOKHEAT;
on|off yylval=!strcmp(yytext,"on"); return STATE;
target return TOKTARGET;
temperature return TOKTEMPERATURE;
\n /* ignore end of line */;
[ \t]+ /* ignore whitespace */;
%%
</screen>
ÅäÅ«ÀÌ ¼ýÀÚÀÏ °æ¿ì atoi¸¦ ÅëÇØ¼ ¹Þ¾Æ¿Â ÅäÅ«(yytext)¸¦ ¼ýÀÚ·Î º¯È¯ÇßÀ½À»
¾Ë¼ö ÀÖ´Ù. º¯È¯µÈ °ªÀº yylvalÀ» ÅëÇØ¼ bisonÄڵ忡¼ »ç¿ëÇÒ ¼ö ÀÖµµ·Ï
¸®ÅϺ¯¼ö NUMBERÀ» ÅëÇØ¼ ¸®ÅÏÇÑ´Ù.
¶ÇÇÑ "on"À» ¸¸³µÀ» °æ¿ì 1À» ¸®ÅÏÇϵµ·Ï Çß´Ù.
</para>
<para>
ÀÌÁ¦ Bison Äڵ忡¼ yylvalÀ» ÅëÇØ¼ ³Ñ¾î¿Â °ªÀ» ÀÌ¿ëÇØ¼ ¾î¶² ÀÛ¾÷À»
°¡´ÉÇϵµ·Ï ÄÚµùÇØ Áֱ⸸ ÇÏ¸é µÈ´Ù. ´Ù¸¥ ºÎºÐÀº ¸ðµÎ µ¿ÀÏÇÏ´Ï ¾Æ·¡ÀÇ ºÎºÐ¸¸
¼öÁ¤ÇÏ¸é µÈ´Ù.
<screen>
heat_switch:
TOKHEAT STATE
{
if($2)
printf("\tHeat turned on\n");
else
printf("\tHeat turned off\n");
}
;
target_set:
TOKTARGET TOKTEMPERATURE NUMBER
{
printf("\tTemperature set %d\n", $3);
}
;
</screen>
ÀÌÇØ´Â ½¬¿ï °ÍÀÌ´Ù. ÅäÅ«ÀÇ °¢ À̸§ÀÇ ¼ø¼´ë·Î $1, $2.. ÇØÁÖ´Â Á¤µµ·Î
ÅäÅ«ÀÌ ³Ñ°ÜÁÖ´Â °ªÀ» ¹Þ¾Æ¿Ã ¼ö ÀÖ´Ù. heat_switchÀÇ °æ¿ì µÎ¹øÂ° ÅäÅ«°ªÀÎ
STATE·Î °ªÀÌ ³Ñ¾î¿À¹Ç·Î "$2"¸¦ ÀÌ¿ëÇÏ¸é ¹Þ¾Æ¿Ã ¼ö ÀÖ´Ù. ó¸®ÄÚµå´Â
°£´ÜÇÏ´Ù. 1À̸é on, 2¸é off°ü·Ã ¸Þ½ÃÁö¸¦ »Ñ·ÁÁÖµµ·Ï ¸¸µé¾ú´Ù.
</para>
<para>
tatget_set ¿ª½Ã µ¿ÀÏÇÑ ¹æ¹ýÀ¸·Î ¼öÁ¤Çß´Ù. ¿Âµµ °ªÀº NUMBER ÅäÅ«°ªÀ¸·Î
³Ñ¾î¿ÈÀ¸·Î $3¸¦ ÀÌ¿ëÇØ¼ ¹Þ¾Æ¼ À̸¦ Ãâ·ÂÇß´Ù.
</para>
<para>
ÄÄÆÄÀÏ Å×½ºÆ®¸¦ ÇÏ¸é ´ÙÀ½°ú °°Àº °á°ú¸¦ È®ÀÎÇÒ ¼ö ÀÖÀ» °ÍÀÌ´Ù.
<screen>
# ./example5
heat on
Heat turned on
heat off
Heat turned off
target temperature 50
</screen>
</para>
</section>
<section>
<title>°è»ê±â¸¦ ¸¸µé¾î º¸ÀÚ</title>
<para>
À̹ø¿¡´Â °è»ê±â ÇÁ·Î±×·¥À» ¸¸µé¾î º¸µµ·Ï ÇÏÀÚ. ¾Õ¼ÀÇ
¿¹Á¦Ã³·³ flex¿Í bisonÀÇ ÀÛµ¿¹æ½Äµµ ÇÔ²² ¼³¸íÇϵµ·Ï ÇϰڴÙ.
</para>
<para>
°è»ê±â ÇÁ·Î±×·¥Àº »çÄ¢¿¬»êÀ» Çϴµ¥, "()"µµ 󸮸¦ ÇÒ °ÍÀÌ´Ù.
¶ÇÇÑ °ªÀ» º¯¼ö¿¡ ÀúÀåÇÏ´Â ±â´É±îÁö¸¦ Ãß°¡ÇÒ °ÍÀÌ´Ù. ¾Æ½Ã°ÚÁö¸¸
°è»ê±â ÇÁ·Î±×·¥À» ÀÛ¼ºÇÔ¿¡ ÀÖ¾î¼ ()󸮸¦ ÇÑ´Ù´Â°Ô ±×¸® °£´ÜÇѰÔ
¾Æ´Ï¶ó´Â°É ÀÌÇØ ÇÒ°ÍÀÌ´Ù. ±×·¯³ª ÀÌ ¿¹Á¦¸¦ ÅëÇØ¼ flex¿Í bisonÀ» ¾´´Ù¸é
±×¸® ¾î·ÆÁö ¾Ê°Ô ÀÛ¼º °¡´ÉÇÏ´Ù´Â °ÍÀ» ¾Ë ¼ö ÀÕÀ» °ÍÀÌ´Ù.
</para>
<para>
°è»ê±â ÇÁ·Î±×·¥¿¡¼´Â ÅäÅ«À¸·Î INTEGER¿Í VARIABLE¸¦ ¼±¾ðÇÑ´Ù.
INTEGERÀº ÇÇ¿¬»êÀÚ¿¡ ´ëÇÑ ÅäÅ«À» ¸¸³µÀ» ¶§ »ç¿ëÇÏ´Â ÅäÅ«°ªÀ̸ç,
VARIABLE´Â º¯¼ö¸¦ ¸¸³µÀ» ¶§ »ç¿ëÇÒ ÅäÅ« °ªÀÌ´Ù.
¿©·¯ºÐÀÌ bison¸¦
½ÇÇà ½ÃŲ´Ù¸é cal.tab.h ÆÄÀÏÀ» º¼ ¼ö ÀÖÀ» °Çµ¥, ´ÙÀ½°ú °°Àº Äڵ带
Æ÷ÇÔÇϰí ÀÖÀ» °ÍÀÌ´Ù.
<screen>
#ifndef YYSTYPE
#define YYSTYPE int
#endif
#define INTEGER 258
extern YYSTYPE yylval;
</screen>
bisonÀº ÀÌ ÀÎŬ·çµå ÆÄÀÏÀ» Æ÷ÇÔÇØ¼ ¼±¾ðµÈ ÅäÅ«°ªÀ» ÀÌ¿ëÇÒ ¼ö ÀÖ°Ô µÈ´Ù.
ÅäÅ«À» ¾ò±â À§Çؼ bison´Â yylex¸¦ È£ÃâÇÏ°Ô µÈ´Ù. yylex´Â int°ªÀ»
¸®ÅÏÇϴµ¥ ¹Ù·Î À§¿¡¼ Á¤ÀÇµÈ ÅäÅ«¿¡ ´ëÇÑ intÇü °ªÀ» ¸®ÅÏÇÏ°Ô µÈ´Ù.
ÅäÅ«¿¡ ´ëÇÑ °ªÀº ¿Âµµ°è¿¹Á¦ ¿¡¼ ¼³¸íÇßµíÀÌ yylvalÀ» ÅëÇØ¼ ¸®ÅÏ
ÇÒ ¼ö ÀÖ´Ù.
<screen>
[0-9]+ {
yylval = atoi(yytext);
return INTEGER;
}
</screen>
yylval¿¡´Â intÇü µ¥ÀÌÅͰ¡ ÀúÀåµÇ°í, ÅäÅ«°ªÀ¸·Î INTEGER¸¦ ¸®ÅÏÇÏ°Ô µÈ´Ù.
yylvaluÀº YYSTYPE·Î ¼±¾ðµÇ¾î ÀÖ´Ù. ÅäÅ«°ªÀº 0-255±îÁö »ç¿ë°¡´É ÇÏ´Ù.
</para>
<para>
ÀÌÁ¦ ¿¬»êÀÚµé°ú ()¿¡ ´ëÇÑ ÅäÅ«À» ¾ò¾î¿Í¾ß ÇÑ´Ù.
<screen>
[-+()=/*\n] {return *yytext;}
</screen>
±×¸®°í º¯¼ö¿¡ ´ëÇÑ ÅäÅ«µµ ¾ò¾î¿Í¾ß ÇÑ´Ù. º¯¼ö¸íÀº ¿µ¹® ¹®ÀÚ Çϳª¸¸
»ç¿ëÇÒ ¼ö ÀÖµµ·Ï Á¦ÇÑÇϵµ·Ï ÇϰڴÙ.
<screen>
[a-z] {
yylval = *yytext - 'a';
return VARIABLE
}
</screen>
</para>
<para>
bison ¹®¹ý¿¡¼ÀÇ ÇÙ½ÉÀº °¢ ¿¬»êÀÚ¿¡ ¸Âµµ·Ï ¿¬»êÀ» ½ÇÇàÇϰí,
°ýÈ£¸¦ ¸¸³µÀ» °æ¿ì ¿ì¼± ¿¬»êÇÒ ¼ö ÀÖ¾î¾ß ÇÑ´Ù´Â Á¡ÀÌ´Ù.
<screen>
expr:
INTEGER
| VARIABLE { $$ = sym[$1]; }
| expr '+' expr { $$ = $1 + $3; }
| expr '-' expr { $$ = $1 + $3; }
| expr '*' expr { $$ = $1 + $3; }
| expr '/' expr { $$ = $1 / $3; }
| '(' expr ')' { $$ = $2; }
;
</screen>
ÇϳªÀÇ ¿¬»ê ¹®Àå¿¡´Â a + c - d * c ¿Í °°Àº ¿©·¯°³ÀÇ ¿¬»êÀÚ°¡ »ç¿ëµÉ ¼ö
ÀÖÀ¸¹Ç·Î À̹®Á¦¸¦ ÇØ°áÇϱâ À§Çؼ´Â left-recursionÀ» ÀÀ¿ëÇØ¼ °³Ç๮ÀÚ¸¦
¸¸³¯¶§±îÁö ¿¬»êÀÚ¿Í ÇÇ¿¬»çÀÚ¸¦ °Ë»çÇÏ¸é¼ °è»êÀ» ÇØ¾ß ÇÑ´Ù.
<xref linkend="pic1">À» º¸¸é ÀÌ·¯ÇÑ °úÁ¤ÀÌ ÀÌÇØ°¡ °¥°ÍÀÌ´Ù. ¿ì¸®´Â
ÀÌ ¹®Á¦¸¦ ÇØ°áÇϱâ À§Çؼ ¿ì¼± parse ½ºÅÃÀ» ¸¸µçÈÄ ½ºÅÃÀÇ °¡Àå
¾Æ·¡(À§¶ó°í ÇØµµ °ü°è ¾ø´Ù)¿¡¼ ºÎÅÍ Â÷·Ê´ë·Î ¿¬»êÀ» ÇØ¾ß ÇÑ´Ù.
ÀÌ·¯ÇÑ ½ºÅø¸µå´Â ÀÛ¾÷Àº ¹°·Ð ÇÁ·Î±×·¡¸Ó°¡
Á÷Á¢ÇÒ ÇÊ¿ä ¾ø´Ù. ¹®¹ý¸¸ Àß ¸¸µé¾î ÁÖ¸é bison¿¡¼ ¾Ë¾Æ¼ ÇØÁØ´Ù.
½ºÅÿ¡ ¹Ð¾î ³Ö±â À§Çؼ expr:·êÀ» »ç¿ëÇÑ´Ù. ¸¸µé¾îÁø ½ºÅÿ¡ ¹Ð¾î ³Ö±â
À§Çؼ expr '+' expr ¸¦ »ç¿ëÇÏ¸é µÈ´Ù. ¿À¸¥ ÂÊ¿¡ ÀÖ´Â exprÀº ½ºÅÃÀÇ
¿À¸¥ÂÊ °ªÀ̰í, ¿ÞÂÊÀÇ exprÀº ½ºÅÃÀÇ ¿ÞÂÊ °ªÀ̵ȴÙ. C Äڵ忡¼´Â
ÀÌ °ªµéÀ» $1°ú $3¸¦ ÅëÇØ¼ ¾ò¾î¿Ã ¼ö ÀÖ´Ù. $2¿¡´Â ¿¬»êÀÚ°¡ µé¾î °¡°Ô
µÈ´Ù. $$Àº °è»êµÈ °ªÀ» ½ºÅÃÀÇ °¡Àå ¾Æ·¡·Î ¹Ð¾î ³ÖÀ¸¶ó´Â Ç¥½Ã´Ù.
</para>
<para>
()¸¦ ¸¸³µÀ» °æ¿ì ÀÌ ¿¬»êÀº ¿ì¼±ÀûÀ¸·Î ÀÌ·ç¾î Á®¾ß ÇÑ´Ù. ±×·¯¹Ç·Î ()¾È¿¡
ÀÖ´Â ¿¬»êµé ÀÚü¸¦ ½ºÅÃÀÇ °¡Àå ¾Æ·¡·Î ¹Ð¾î ³Ö¾î¾ß ÇÒ °ÍÀÌ´Ù. À̸¦
À§Çؼ '(' expr ')' {$$ = $2;}°¡ »ç¿ëÇϰí ÀÖ´Ù.
</para>
<para>
´ÙÀ½Àº flex¿Í bisonÀÇ ¿ÏÀüÇÑ ÄÚµå·Î ÆÄÀÏÀ̸§Àº cal.l, cal.y·Î Çϸç,
À§¿¡¼ ºüÁø ¸î°¡Áö ³»¿ëµéÀº ÁÖ¼®À» ÅëÇØ¼ ¼³¸íÇϵµ·Ï ÇϰڴÙ.
</para>
<para>
¿¹Á¦ : cal.l
<screen>
%{
#include <stdlib.h>
void yyerror(char *);
#include "mycal.tab.h"
%}
%%
/* º¯¼ö¸íÀ» À§ÇÑ VARIABLE ÅäÅ«À» µÇµ¹·Á ÁØ´Ù */
/* º¯¼ö¸íÀº a-z ±îÁö »ç¿ëµÉ ¼ö ÀÖ´Ù. */
/* ¸®ÅÏµÈ °ªÀº cal.y¿¡¼ symÅ×À̺íÀ» ¸¸µé±â À§Çؼ »ç¿ëµÈ´Ù. */
[a-z] {
yylval = *yytext - 'a';
return VARIABLE;
}
/* ¼ýÀÚ¸¦ ¸¸³µÀ» ¶§ */
[0-9]+ {
yylval = atoi(yytext);
return INTEGER;
}
/* ¿¬»êÀÚ¸¦ ¸¸³µÀ» ¶§ */
[-+()=/*\n] {return *yytext;}
[ \t] ; /* ¹«½ÃÇÑ´Ù */
. yyerror("invalid character");
%%
int yywrap(void)
{
return 1;
}
</screen>
¿¹Á¦ : cal.y
<screen>
%token INTEGER VARIABLE
%left '+' '-'
%left '*' '/'
%{
void yyerror(char *);
int yylex(void);
int sym[26];
%}
%%
program:
program statement '\n'
|
;
/* º¯¼ö¸¦ ¸¸³µÀ» °æ¿ì */
/* º¯¼ö¸íÀÇ ÅäÅ«°ªÀ» ÀÌ¿ëÇØ¼ ½Éº¼¸¯ Å×À̺íÀ» ¸¸µç´Ù */
/* ¸¸¾à º¯¼ö¸íÀÌ 'a'¶ó¸é ÅäÅ«°ªÀº 0ÀÌ ¸®Åϵǰí */
/* sym[0] ¿¡ ¿¬»ê°á°ú°¡ µé¾î°¡°Ô µÈ´Ù. */
statement:
expr { printf("°è»ê°á°ú %d\n", $1); }
| VARIABLE '=' expr { sym[$1] = $3; }
;
expr:
INTEGER
| VARIABLE { $$ = sym[$1]; }
| expr '+' expr { $$ = $1 + $3; }
| expr '-' expr { $$ = $1 - $3; }
| expr '*' expr { $$ = $1 * $3; }
| expr '/' expr { $$ = $1 / $3; }
| '(' expr ')' { $$ = $2; }
;
%%
void yyerror(char *s)
{
printf("%s\n", s);
return 0;
}
int main(void)
{
yyparse();
return 0;
}
</screen>
´ÙÀ½Àº Å×½ºÆ® °á°ú´Ù. °ýÈ£¸¦ ÅëÇÑ ¿¬»êÀº ¹°·ÐÀÌ°í ´ÙÁßÀÇ °ýÈ£±îÁö
ó¸®Çϰí ÀÖÀ½À» ¾Ë ¼ö ÀÕ´Ù.
<screen>
# ./cal
a=5*(10+20)
a
°è»ê °á°ú 150
a=10+5+2 +(2*10)
a
°è»ê °á°ú 37
(10*12)/(3*2)
°è»ê °á°ú 20
b=((52+32)/(2*1)+(16*3))+(22*2)
b
°è»ê °á°ú 134
</screen>
</para>
</section>
</section>
</article>
|
|
|
EmailÀ» ±âÀÔÇϸé, ´ñ±ÛÀÌ ¸ÞÀÏ·Î Àü´ÞµË´Ï´Ù. |
|