PDA

View Full Version : حرفه ای: ساخت Compiler و یک زبان برنامه نویسی جدید



صفحه : 1 [2]

amin32
دوشنبه 17 بهمن 1390, 22:01 عصر
ببخش ولی تا من مثال دقیق نبینم , قانع نمیشم. تو کتابخانه های gcc هرچی گشتم یک چنین چیزی ندیدم. میتونی مثال واضح از یک زبان و کامپایلر معروف بیاری.

amin32
دوشنبه 17 بهمن 1390, 22:05 عصر
ببین مثلا شما فرض کن ما برای

Variable1 = Variable2
باید این کد رو تولید کنیم :

MOV AX,variable2
MOV Variable1,AX
خوب می آیم مثلا این رو تعریف می کنیم به عنوان ماکرو:

macro ThreeAddress_MOVE Operand1,CPURegister,Operand2
{
MOV CPURegister,Operand2
MOV Operand1,CPURegister
}

بعد مثلا این طوری کد 3 آدرسی تولید می کنیم:


ThreeAddress_MOVE variable1,AX,variable2

منظورم این طوری بود.

این رو بگم که اگه منظورت از کد سه آدرسه همون کد زبان میانی ما هست , اشتباهه و باید از همون فرمهایی که گذاشتم تبعیت کنه. بازم میگم نیاز به تحقیق داره.

IamOverlord
دوشنبه 17 بهمن 1390, 22:21 عصر
خوب اگه شما می خواید دستورات پایه مون سطح بالا باشه، قبول، تجربه اش ضرر نداره.
در مورد کد سه آدرسه من هر چه قدر فکر می کنم مزیت روش قبلی رو نسبت به این حالت نمی فهمم:

Instruction FirstOperand , SecondOperand , ThirdOperand
:متفکر:

amin32
دوشنبه 17 بهمن 1390, 22:29 عصر
خوب اگه شما می خواید دستورات پایه مون سطح بالا باشه، قبول، تجربه اش ضرر نداره.
در مورد کد سه آدرسه من هر چه قدر فکر می کنم مزیت روش قبلی رو نسبت به این حالت نمی فهمم:

Instruction FirstOperand , SecondOperand , ThirdOperand
:متفکر:

بله این هم میتونه نوعی زبان میانی باشه ولی چون گفتید کد سه آدرسه هست , خواستم تذکر بدم که کد سه آدرسه نیست.
الان به نظرم اگه بخوایم دستورات پایه رو به زبان سطح بالا تعریف کنیم فکر میکنم اولویت با ورودی خروجی باشه.

amin32
دوشنبه 17 بهمن 1390, 22:35 عصر
با اینکه خودم مایلم کار اصولی پیش بره ولی احساس میکنم این کد میانی یکم کارو طولانی میکنه. نظرتون چیه؟ کد مبدآ رو مستقیمآ به اسمبلی تبدیل نکنیم؟؟؟!!!!:متفکر:

IamOverlord
دوشنبه 17 بهمن 1390, 22:36 عصر
خوب انواع ورودی و خروجی ها چی هستن؟

IamOverlord
دوشنبه 17 بهمن 1390, 22:37 عصر
با اینکه خودم مایلم کار اصولی پیش بره ولی احساس میکنم این کد میانی یکم کارو طولانی میکنه. نظرتون چیه؟ کد مبدآ رو مستقیمآ به اسمبلی تبدیل نکنیم؟؟؟!!!!:متفکر:

نمی گم کد مبدا (اصلاح شد) مستقیما به کد Assembly تبدیل بشه، می گم فقط مشابه باشه با اون کد. این طوری راحت تره، غیر اصولی هم نیست، هر کی هر شکل کد میانی ای که می خواد می تونه داشته باشه.

amin32
دوشنبه 17 بهمن 1390, 22:39 عصر
فکر میکنم اول باید به فکر ورودی خروجی ( خواندن و نوشتن ) در کنسول باشیم و بعد هم کار با فایل!

amin32
دوشنبه 17 بهمن 1390, 22:42 عصر
نمی گم کد میانی مستقیما به کد Assembly

این نظر خود من بود. پس شما نظرت اینه که اول به کد میانی تبدیل بشه بعد به اسمبلی دیگه. درسته ؟

IamOverlord
دوشنبه 17 بهمن 1390, 22:45 عصر
دقیـقـا...

amin32
دوشنبه 17 بهمن 1390, 22:46 عصر
نمی گم کد میانی مستقیما به کد Assembly تبدیل بشه، می گم فقط مشابه باشه با اون کد. این طوری راحت تره، غیر اصولی هم نیست، هر کی هر شکل کد میانی ای که می خواد می تونه داشته باشه.

فکر میکنم یک اشتباهی شد. من پیشنهاد نکردم کد میانی مستقیم به اسمبلی تبدیل بشه چون باید مستقیم باشه. پیشنهاد من این بود که مرحله کد میانی حذف بشه و کد مبدآ مستقیمآ به اسمبلی تبدیل بشه. این فقط یه پیشنهاده. نظرت چیه؟

IamOverlord
دوشنبه 17 بهمن 1390, 22:46 عصر
فکر میکنم اول باید به فکر ورودی خروجی ( خواندن و نوشتن ) در کنسول باشیم و بعد هم کار با فایل!

نظرتون چیه در مورد این که دستورات ورودی و خروجی ساختار فراخوانی شون شبیه بقیه ی زیربرنامه ها باشه؟!

IamOverlord
دوشنبه 17 بهمن 1390, 22:47 عصر
فکر میکنم اول باید به فکر ورودی خروجی ( خواندن و نوشتن ) در کنسول باشیم و بعد هم کار با فایل!

نظرتون چیه در مورد این که دستورات ورودی و خروجی ساختار فراخوانی شون شبیه بقیه ی زیربرنامه ها باشه؟!

IamOverlord
دوشنبه 17 بهمن 1390, 22:51 عصر
فکر میکنم یک اشتباهی شد. من پیشنهاد نکردم کد میانی مستقیم به اسمبلی تبدیل بشه چون باید مستقیم باشه. پیشنهاد من این بود که مرحله کد میانی حذف بشه و کد مبدآ مستقیمآ به اسمبلی تبدیل بشه. این فقط یه پیشنهاده. نظرت چیه؟

آه...! ببخشید.
پست اصلاح شد. منظورم کد مبدا بود.
من هم موافقم با این که کد مبدا یا مستقیم به کد Assembly تبدیل بشه یا خیلی مشابه کد های Assembly مون باشه همون طوری که مثال زدم با macro.

amin32
دوشنبه 17 بهمن 1390, 22:51 عصر
نظرتون چیه در مورد این که دستورات ورودی و خروجی ساختار فراخوانی شون شبیه بقیه ی زیربرنامه ها باشه؟!

ببین مثلآ توی زبان c یا basic فکر نمیکنم که شبیه هم باشن. بهتره ما هم به همین رویه عمل کنیم.

amin32
دوشنبه 17 بهمن 1390, 22:55 عصر
ولی بهتره خواندن و نوشتن در کنسول با خواندن و نوشتن در فایل به نوعی یک پارچه باشن.

IamOverlord
دوشنبه 17 بهمن 1390, 23:03 عصر
برای کار با فایل موافقم،
اما در مورد خوندن و نوشتن به نظرم مثل تابع و زیربرنامه باشن بهتره.

IamOverlord
دوشنبه 17 بهمن 1390, 23:07 عصر
اصلا مثل C هر دو روش...!:لبخند:

amin32
دوشنبه 17 بهمن 1390, 23:08 عصر
OK!
ساختار معرفی کن.

IamOverlord
دوشنبه 17 بهمن 1390, 23:13 عصر
Console.WriteLine ' minevise mire khatte payin
Console.Write ' faghat minevise
Console.ReadLine ' mikhoone ta yaroo enter ro bezane
Console.ReadCharacter ' faghat ye character mikhoone
...

این Console قبلشو چی کار کنیم...؟

amin32
دوشنبه 17 بهمن 1390, 23:15 عصر
اصلا مثل C هر دو روش...!:لبخند:

الان که دارم خوب فکر میکنم , اصلآ امکان اینکه خواندن و نوشتن در کنسول رو به شکل تابع در بیاریم نیست چون باز مجبوریم از دستورات اسمبلی در تعریف تابع استفاده کنیم. ولی در مورد فراخوانیش به شکل توابع مشکلی نیست.

amin32
دوشنبه 17 بهمن 1390, 23:20 عصر
Console.WriteLine ' minevise mire khatte payin
Console.Write ' faghat minevise
Console.ReadLine ' mikhoone ta yaroo enter ro bezane
Console.ReadCharacter ' faghat ye character mikhoone
...

این Console قبلشو چی کار کنیم...؟

بهتر نیست از دستورات به تنهایی استفاده بشه؟ (بدون console) . چون این در مفاهیم فعلی زبانمو نیست. به خاطر همین نقطه و console مجبوریم مفاهیم جدیدی رو در زبانمو حمایت کنیم ( شی گرایی!)

IamOverlord
دوشنبه 17 بهمن 1390, 23:20 عصر
یا:


use 'iostream'
use 'ScreenClass'

object obj01 : ScreenInterface ' An object from ScreenClass

obj01.WriteLine ...
obj01.ReadLine ...

' Note : ScreenClass written with iostream routines.

' bara in ke ghablesh console byad:

object Console : ScreenInterface

IamOverlord
دوشنبه 17 بهمن 1390, 23:24 عصر
الان که دارم خوب فکر میکنم , اصلآ امکان اینکه خواندن و نوشتن در کنسول رو به شکل تابع در بیاریم نیست چون باز مجبوریم از دستورات اسمبلی در تعریف تابع استفاده کنیم. ولی در مورد فراخوانیش به شکل توابع مشکلی نیست.

منظورتون رو متوجه نشدم. پیاده سازی توابع زیربرنامه ها در Assembly که مشکلی نداره...

amin32
دوشنبه 17 بهمن 1390, 23:25 عصر
یا:


use 'iostream'
use 'ScreenClass'

object obj01 : ScreenInterface ' An object from ScreenClass

obj01.WriteLine ...
obj01.ReadLine ...

' Note : ScreenClass written with iostream routines.

' bara in ke ghablesh console byad:

object Console : ScreenInterface

وای این که دیگه پیچیده تر شد. بازم میگم چهار تا دستور ساده باشه خیلی بهتره.

IamOverlord
دوشنبه 17 بهمن 1390, 23:28 عصر
بهتر نیست از دستورات به تنهایی استفاده بشه؟ (بدون console) . چون این در مفاهیم فعلی زبانمو نیست. به خاطر همین نقطه و console مجبوریم مفاهیم جدیدی رو در زبانمو حمایت کنیم ( شی گرایی!)

!OK
پس اول غیر شئ گراشو می نویسیم مثل C، بعد می شینیم مثل جناب Stroustrup مفاهیم شئ گرایی رو اضافه می کنیم... :لبخند:

IamOverlord
دوشنبه 17 بهمن 1390, 23:29 عصر
وای این که دیگه پیچیده تر شد. بازم میگم چهار تا دستور ساده باشه خیلی بهتره.

اون چهار تا دستور ساده تو iostream قایم شده بودن!
ولی باشه به هر حال فعلا غیر شئ گراشو می نویسیم بعد ... .

amin32
دوشنبه 17 بهمن 1390, 23:30 عصر
منظورتون رو متوجه نشدم. پیاده سازی توابع زیربرنامه ها در Assembly که مشکلی نداره...

چون شما گفتید مثل C از هر دو روش, فکر کردم شاید میخواید برای خواندن و نوشتن باز از توابع کتابخانه ای استفاده کنید. بیخیال....
فعلا تکلیف همین دستورات سطح بالا رو مشخص کنیم.

IamOverlord
دوشنبه 17 بهمن 1390, 23:35 عصر
چون شما گفتید مثل C از هر دو روش, فکر کردم شاید میخواید برای خواندن و نوشتن باز از توابع کتابخانه ای استفاده کنید. بیخیال....
فعلا تکلیف همین دستورات سطح بالا رو مشخص کنیم.

OK
ولی منظورم scanf من و cin شما بود!
چون scanf خیلی شبیه با زیربرنامه ها و توابعه و cout هم که نه!

اصلا زیاد مهم نیست، چون اگه یه چیزی مثل cout پیاده سازی کنیم که شبیه زیربرنامه ها نباشه، خیلی راحت می شه زیربرنامش هم نوشت دیگه...!

خوب حالا نظر شما برای ورودی و خروجی چیه؟
این که ورودی و خروجی Console و File ها شبیه هم باشن جالب بود اما چه طوری؟

amin32
دوشنبه 17 بهمن 1390, 23:44 عصر
OK
خوب حالا نظر شما برای ورودی و خروجی چیه؟
این که ورودی و خروجی Console و File ها شبیه هم باشن جالب بود اما چه طوری؟

مثلآ در vb دستور print هم میتونه در نوشتن روی فرم به کار بره هم در نوشتن در فایل.

IamOverlord
چهارشنبه 19 بهمن 1390, 19:01 عصر
مثل QBASIC باشه [تقریبا]؟!

amin32
چهارشنبه 19 بهمن 1390, 19:29 عصر
نباید شبیه زبانی دیگه باشه؟
در ضمن همونطور که گفتم من فقط تا اواسط اسفند, وقت آزاد دارم. بعدش به خاطر درسهام نمیتونم فعلآ وقتم رو برای این کار بگذارم.:افسرده:

IamOverlord
چهارشنبه 19 بهمن 1390, 19:56 عصر
کی فکر می کنی وقتت آزاد می شه؟!

amin32
چهارشنبه 19 بهمن 1390, 20:04 عصر
تا آخر ترم !

ولی متآسفانه تا همینجاش خیلی وقت و از دست دادیم.
شاید بتونم تا اون موقع تحلیلگر نحوی رو تکمیل کنم و باقی رو بذاریم برای بعد.

Slytherin
جمعه 12 اسفند 1390, 12:59 عصر
اعتماد به نفستون توی حلقم:لبخند:
صفحه 1 تایپیک بودم، اونجا بحث بود که ساختار لغات مشخص بشه! الان اومدم صفحه 29 می بینم که هنوز داره در مورد ساختار کلمات کلیدی و نحو برنامه بحث میشه!:لبخند:
کارتون قابل تحسین هست ولی فکر کنم حتی اگر بخواهید به یک نتیجه ساده برسید سال ها طول بکشه...
یک پیشنهاد:
چون پروژه تجاری نیست صرفا جنبه آموزشی داره به نظرم اول یک زبان ناقص طراحی کنید و اگر جواب داد بعد روی کامل کردنش تحت یک پروژه کاملا جدید و مستقل کار کنید...

IamOverlord
جمعه 12 اسفند 1390, 13:20 عصر
مشکل وقته! وگرنه کار ادامه پیدا می کنه. کس دیگه هم غیر از جناب amin32 (http://barnamenevis.org/member.php?162007-amin32) نیست که کارو سریع تر ادامه بدیم...

manocher.a
چهارشنبه 02 فروردین 1391, 22:04 عصر
سلام بر دوستان عزیز
ضمن عرض تبریک سال نو میخواستم عرض کنم من هم تاپیک دارم دنبال میکنم ولی خبری نشد حالا که من میخوام یک پروژه تجاری اینجا ارائه بدم بلکه شما دوستان بتونید روی این موضوع کمکی به من بکنید شاید روش اجرا جنبه ایی آموزشی هم شد
من در حال نوشتن یک پلتفورم برای بازار فارکس هستم و میخوام با ساخت کامپلیر ساده بتونم اندیکاتورهای نوشته شده در این مورد به این پلتفرم اضافه کنم در زیز هم نمونه یکی از اندیکاتورها اضافه کردم حالا ضمن نوشته های قبلی دوستان هر کدوم از دوستان که توانایی دارن راهنمایی کنند(از همه دوستان تشکر میکنم)

//+------------------------------------------------------------------+
//| Heiken Ashi.mq4 |
//| Copyright c 2004, MetaQuotes Software Corp. |
//| http://www.metaquotes.net |
//+------------------------------------------------------------------+
//| For Heiken Ashi we recommend next chart settings ( press F8 or |
//| select on menu 'Charts'->'Properties...'): |
//| - On 'Color' Tab select 'Black' for 'Line Graph' |
//| - On 'Common' Tab disable 'Chart on Foreground' checkbox and |
//| select 'Line Chart' radiobutton |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2004, MetaQuotes Software Corp."
#property link "http://www.metaquotes.net"

#property indicator_chart_window
#property indicator_buffers 4
#property indicator_color1 Red
#property indicator_color2 White
#property indicator_color3 Red
#property indicator_color4 White
#property indicator_width1 1
#property indicator_width2 1
#property indicator_width3 3
#property indicator_width4 3

//----
extern color color1 = Red;
extern color color2 = White;
extern color color3 = Red;
extern color color4 = White;
//---- buffers
double ExtMapBuffer1[];
double ExtMapBuffer2[];
double ExtMapBuffer3[];
double ExtMapBuffer4[];
//----
int ExtCountedBars=0;
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//|------------------------------------------------------------------|
int init()
{
//---- indicators
SetIndexStyle(0,DRAW_HISTOGRAM, 0, 1, color1);
SetIndexBuffer(0, ExtMapBuffer1);
SetIndexStyle(1,DRAW_HISTOGRAM, 0, 1, color2);
SetIndexBuffer(1, ExtMapBuffer2);
SetIndexStyle(2,DRAW_HISTOGRAM, 0, 3, color3);
SetIndexBuffer(2, ExtMapBuffer3);
SetIndexStyle(3,DRAW_HISTOGRAM, 0, 3, color4);
SetIndexBuffer(3, ExtMapBuffer4);
//----
SetIndexDrawBegin(0,10);
SetIndexDrawBegin(1,10);
SetIndexDrawBegin(2,10);
SetIndexDrawBegin(3,10);
//---- indicator buffers mapping
SetIndexBuffer(0,ExtMapBuffer1);
SetIndexBuffer(1,ExtMapBuffer2);
SetIndexBuffer(2,ExtMapBuffer3);
SetIndexBuffer(3,ExtMapBuffer4);
//---- initialization done
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//---- TODO: add your code here

//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
double haOpen, haHigh, haLow, haClose;
if(Bars<=10) return(0);
ExtCountedBars=IndicatorCounted();
//---- check for possible errors
if (ExtCountedBars<0) return(-1);
//---- last counted bar will be recounted
if (ExtCountedBars>0) ExtCountedBars--;
int pos=Bars-ExtCountedBars-1;
while(pos>=0)
{
haOpen=(ExtMapBuffer3[pos+1]+ExtMapBuffer4[pos+1])/2;
haClose=(Open[pos]+High[pos]+Low[pos]+Close[pos])/4;
haHigh=MathMax(High[pos], MathMax(haOpen, haClose));
haLow=MathMin(Low[pos], MathMin(haOpen, haClose));
if (haOpen<haClose)
{
ExtMapBuffer1[pos]=haLow;
ExtMapBuffer2[pos]=haHigh;
}
else
{
ExtMapBuffer1[pos]=haHigh;
ExtMapBuffer2[pos]=haLow;
}
ExtMapBuffer3[pos]=haOpen;
ExtMapBuffer4[pos]=haClose;
pos--;
}
//----
return(0);
}
//+------------------------------------------------------------------+

amin32
شنبه 17 تیر 1391, 11:19 صبح
سلام من برگشتم.
خب بعد از این وقفه طولانی تصمیم گرفتم دوباره تا جایی که میتونم روی پروژه کار کنم. البته این رو بگم که باز هم بودنم در پروژه قطعی نیست و ممکنه به خاطر مشکلات شخصی زیادی که دارم پروژه رو رها کنم.همینجا از دوستان و اساتید دیگه هم دعوت میکنم که اگه در پروژه مشارکت کنند.بگذریم...
یک تغییر کوچیک مد نظرم هست و اون اینه که به خاطر جلوگیری از بعضی سوء استفاده های احتمالی تا زمان تکمیل شدن کامل پروژه کدهای اصلی فازها فقط در اختیار اعضای گروه قرار میگیره. البته بحث و تحلیل کدها و الگوریتم ها و مسائل دیگه به صورت عمومی انجام میشه.
یک سوالی هم برام پیش اومده .در مورد استفاده از اسمبلر FASM که ما اینقدر برای تکمیل پروژه روش حساب کردیم آیا مشکلی از لحاظ قانونی و کپی رایت نداره.

IamOverlord
شنبه 17 تیر 1391, 15:05 عصر
...سلام!
فکر می کنم مشکلی نباشه، این جا رو ببینید: www.bttr-software.de/forum/forum_entry.php?id=8727 (http://www.bttr-software.de/forum/forum_entry.php?id=8727)

amin32
شنبه 17 تیر 1391, 19:17 عصر
خب پس مثل اینکه مشکلی از این بابت نیست.
میرسیم به ساخت EBNF زبان برای پیاده سازی تحلیلگر نحوی.

IamOverlord
شنبه 17 تیر 1391, 22:47 عصر
فکر می کنم قبلا یه کدی برای تحلیلگر لغوی نوشته بودین...
خوب برای ساختار EBNF یه ساحتار کلی پیشنهاد بدید، روش کار کنیم، یه سری چیزهای اصولی هم که در اکثر ساختار ها مشترکه،...

amin32
یک شنبه 18 تیر 1391, 08:13 صبح
فکر می کنم قبلا یه کدی برای تحلیلگر لغوی نوشته بودین...
خوب برای ساختار EBNF یه ساحتار کلی پیشنهاد بدید، روش کار کنیم، یه سری چیزهای اصولی هم که در اکثر ساختار ها مشترکه،...

بله تحلیلگر لغوی تقریبآ کامله. در مورد ساختار نحوی هم که قبلآ در موردش بحث کردیم:

http://barnamenevis.org/showthread.php?296021-%D8%B3%D8%A7%D8%AE%D8%AA-Compiler-%D9%88-%DB%8C%DA%A9-%D8%B2%D8%A8%D8%A7%D9%86-%D8%A8%D8%B1%D9%86%D8%A7%D9%85%D9%87-%D9%86%D9%88%DB%8C%D8%B3%DB%8C-%D8%AC%D8%AF%DB%8C%D8%AF&p=1428198&viewfull=1#post1428198

و برای ساختار حلقه:
http://barnamenevis.org/showthread.php?296021-%D8%B3%D8%A7%D8%AE%D8%AA-Compiler-%D9%88-%DB%8C%DA%A9-%D8%B2%D8%A8%D8%A7%D9%86-%D8%A8%D8%B1%D9%86%D8%A7%D9%85%D9%87-%D9%86%D9%88%DB%8C%D8%B3%DB%8C-%D8%AC%D8%AF%DB%8C%D8%AF&p=1428655&viewfull=1#post1428655

فقط الان که دارم دقت میکنم با توجه به ساختار حلقه باید کلمه Check رو هم به کلمات کلیدی در تحلیلگر لغوی اضافه بشه که چیز مهمی نیست. الان باید با توجه به ساختاری که با مثال ایجاد کردیم EBNF رو بسازیم ولی باید دقت کنیم که گرامرها نباید ابهام یا بازگشتی چپ داشته باشند.

IamOverlord
یک شنبه 18 تیر 1391, 17:57 عصر
چون تا حالا یه گرامر درست و حسابی ننوشتم، اول یه نگاهی بندازیم به بقیه ی گرامر ها و روی اون ها کار کنیم و بعد گرامر خودمون رو بنویسیم...
این هم یه نمونه ی خوب: rosettacode.org/wiki/BNF_Grammar (http://rosettacode.org/wiki/BNF_Grammar)

emadfa
دوشنبه 19 تیر 1391, 13:40 عصر
سلام بر دوستان.
من همه پست های این تاپیک رو بررسی نکردم ولی تعداد زیادی از اون ها رو خوندم...

به دلیل علاقه ای که به طراحی کامپایلر ( و به شکل خاص تر parse کردن یک متن در نرم افزار خودم ) داشتم با کامپایلر و الگوریتم های طراحی اون آشنایی زیادی دارم...

دوستان... فراموش نکنید که تقریبا در اکثر کامپایلرهای دنیا (یا به عبارتی همه کامپایلرها) دو بخش اول یعنی تحلیلگر لغوی و تحلیلگر نحوی به هیچ عنوان دستی انجام نمی شه... یعنی برای نوشتن تحلیل گر لغوی و نحوی طراحان کامپایلر حتی شاید یک خط کد هم ننویسند... بلکه از ابزارهای آماده استفاده می کنند...
ابزارهای زیادی وجود داره...

به عنوان مثال برای طراحی تحلیلگر لغوی... وقتی زبان و واژگان زبان (توکن ها) رو طراحی کردیم... باید تحت یک فرمت مشخص این توکن ها رو به عنوان ورودی به ابزاری مثل LEX یا FLEX بدیم... خود این ابزار برای ما Scanner رو تولید می کنه و به ما یک کد و برنامه میده...

شما تصور کنید برای طراحی یک کامپایلر برای زبانی مثل C اگر بخوایم Scanner رو دستی طراحی کنیم چقدر کد وحشتناک می شه... DFD ما برای اسکنر مثلا شامل حدود 3000 state می شه... برای طراحی این states با جدول انتقال (Transition-Diagram) یا روش switch-case (دو روش طراحی scanner بدون ابزار) شاید نیاز بشه ماه ها وقت بزاریم... در نهایت هم احتمالا خطا و اشتباه به دلیل پیچیدگی وجود خواهد داشت و البته دو فاکتور مهم در مهندسی نرم افزار یعنی "وقت" و "هزینه" رو از دست میدیم... این رو میشه با ابزار در مدت زمان کوتاهی با دقت بسیار بالا انجام داد (اگر زبان و توکن ها طراحی شده باشه شاید کمتر از چند ساعت برای نوشتن و تولید scanner زمان نیاز باشه) و در عوض تمرکزمون رو روی بهینه سازی ها و تحلیل گر معنایی و سایر قسمت های مهم کامپایلر بزاریم...


برای طراحی parser یا تحلیل گر معنایی هم دقیقا همین طوره... دونستن مفاهیم پارسر مثل (SLR(1 یا گرامرهای (LL(1 یا (CLR(1 یا ... ضروری هست و باید بلد باشیم (چون به ما دید میده و گاهی اوقات حتی کمک هم میکنه) اما در عمل از هیچ کدوم از این ها استفاده نمی کنیم بلکه به عنوان مثال از ابزاری به نام YACC (مخفف Yet Another Compiler Compiler) استفاده می کنیم... ما به ابزار همه گرامر های زبان رو میدیم و ابزار به شکل اتوماتیک الگوریتم تحلیل پایین به بالا (LALR1) رو پیاده سازی می کنه و به ما مثلا کد C می ده.... در واقع تنها کاری که باید انجام بدیم طراحی همه گرامرهای زبان هست نه پیاده سازی parser مربوط به این گرامرها
فراموش نکنید طراحی تحلیل گر نحوی به شکل دستی کار بسیار دقیق و زمانبری هست و البته با وجود این ابزارهای خودکار و قدرتمند بیهوده... چون اگر صدها یا هزاران گرامر داشته باشیم باید برای تک تک گرامرها الگوریتمهای تحلیل نحوی (پایین به بالا یا بالا به پایین) مثلا (LALR(1 (یکی از قویترین الگوریتم های parser پایین به بالا) رو اعمال و پیاده سازی کنیم و چنین کاری با داشتن ابزار بیهوده است...

از این ابزارها و ابزارهای مشابه تقریبا همه شرکت های مشهور حتی طراحان جاوا یا مایکروسافت (برای طراحی کامپایلر) استفاده می کنند. بنابراین پیشنهاد می کنم از نرم افزارهای قدرتمند برای تولید حداقل این دو بخش از کامپایلر استفاده کنید...

موفق باشید...

IamOverlord
دوشنبه 19 تیر 1391, 13:58 عصر
سلام دوست عزیز،
البته توجه داشته باشیم فعلا این پروژه جنبه ی یادگیری و سرگرمی داره، نه جنبه ی تجاری...
اما پیشنهاد خوبیه... :متفکر:

amin32
سه شنبه 20 تیر 1391, 04:07 صبح
سلام بر دوستان.
من همه پست های این تاپیک رو بررسی نکردم ولی تعداد زیادی از اون ها رو خوندم...

به دلیل علاقه ای که به طراحی کامپایلر ( و به شکل خاص تر parse کردن یک متن در نرم افزار خودم ) داشتم با کامپایلر و الگوریتم های طراحی اون آشنایی زیادی دارم...

دوستان... فراموش نکنید که تقریبا در اکثر کامپایلرهای دنیا (یا به عبارتی همه کامپایلرها) دو بخش اول یعنی تحلیلگر لغوی و تحلیلگر نحوی به هیچ عنوان دستی انجام نمی شه... یعنی برای نوشتن تحلیل گر لغوی و نحوی طراحان کامپایلر حتی شاید یک خط کد هم ننویسند... بلکه از ابزارهای آماده استفاده می کنند...
ابزارهای زیادی وجود داره...

به عنوان مثال برای طراحی تحلیلگر لغوی... وقتی زبان و واژگان زبان (توکن ها) رو طراحی کردیم... باید تحت یک فرمت مشخص این توکن ها رو به عنوان ورودی به ابزاری مثل LEX یا FLEX بدیم... خود این ابزار برای ما Scanner رو تولید می کنه و به ما یک کد و برنامه میده...

شما تصور کنید برای طراحی یک کامپایلر برای زبانی مثل C اگر بخوایم Scanner رو دستی طراحی کنیم چقدر کد وحشتناک می شه... DFD ما برای اسکنر مثلا شامل حدود 3000 state می شه... برای طراحی این states با جدول انتقال (Transition-Diagram) یا روش switch-case (دو روش طراحی scanner بدون ابزار) شاید نیاز بشه ماه ها وقت بزاریم... در نهایت هم احتمالا خطا و اشتباه به دلیل پیچیدگی وجود خواهد داشت و البته دو فاکتور مهم در مهندسی نرم افزار یعنی "وقت" و "هزینه" رو از دست میدیم... این رو میشه با ابزار در مدت زمان کوتاهی با دقت بسیار بالا انجام داد (اگر زبان و توکن ها طراحی شده باشه شاید کمتر از چند ساعت برای نوشتن و تولید scanner زمان نیاز باشه) و در عوض تمرکزمون رو روی بهینه سازی ها و تحلیل گر معنایی و سایر قسمت های مهم کامپایلر بزاریم...


برای طراحی parser یا تحلیل گر معنایی هم دقیقا همین طوره... دونستن مفاهیم پارسر مثل (SLR(1 یا گرامرهای (LL(1 یا (CLR(1 یا ... ضروری هست و باید بلد باشیم (چون به ما دید میده و گاهی اوقات حتی کمک هم میکنه) اما در عمل از هیچ کدوم از این ها استفاده نمی کنیم بلکه به عنوان مثال از ابزاری به نام YACC (مخفف Yet Another Compiler Compiler) استفاده می کنیم... ما به ابزار همه گرامر های زبان رو میدیم و ابزار به شکل اتوماتیک الگوریتم تحلیل پایین به بالا (LALR1) رو پیاده سازی می کنه و به ما مثلا کد C می کنه.... در واقع تنها کاری که باید انجام بدیم طراحی همه گرامرهای زبان هست نه پیاده سازی parser مربوط به این گرامرها)
فراموش نکنید طراحی تحلیل گر نحوی به شکل دستی کار بسیار دقیق و زمانبری هست و البته با وجود این ابزارهای خودکار و قدرتمند بیهوده... چون اگر صدها یا هزاران گرامر داشته باشیم باید برای تک تک گرامرها الگوریتمهای تحلیل نحوی (پایین به بالا یا بالا به پایین) مثلا (LALR(1 (یکی از قویترین الگوریتم های parser پایین به بالا) رو اعمال و پیاده سازی کنیم و چنین کاری با داشتن ابزار بیهوده است...

از این ابزارها و ابزارهای مشابه تقریبا همه شرکت های مشهور حتی طراحان جاوا یا مایکروسافت (برای طراحی کامپایلر) استفاده می کنند. بنابراین پیشنهاد می کنم از نرم افزارهای قدرتمند برای تولید حداقل این دو بخش از کامپایلر استفاده کنید...

موفق باشید...

سلام دوست عزیز.
من تا حدودی با حرفتون موافقم یعنی اینکه استفاده از Yacc و bison میتونه به تولید تحلیلگر نحوی سرعت ببخشه. البته فکر میکنم در مورد تحلیلگر لغوی فرق چندانی نداره و ما توستیم اون رو به راحتی به صورت دستی بسازیم. با توجه به تعداد حالتهای لغات:
http://barnamenevis.org/showthread.php?296021-ساخت-Compiler-و-یک-زبان-برنامه-نویسی-جدید&p=1433481&viewfull=1#post1433481

همونطور که دوستمون گفتن چون ما هدفمون بیشتر جنبه یادگیری داره فکر میکنم بهتر باشه به شکل دستی ساخته بشه.بازم ممنون از نظرتون. ازتون دعوت میکنم اگر مایل بودید در پروژه با ما همکاری کنید.

amin32
چهارشنبه 21 تیر 1391, 12:09 عصر
دو تا لینک خوب برای آشنایی بهتر با EBNF و گرامرها:

http://c.comsci.us/syntax/expression/ebnf.html

http://cs.lmu.edu/~ray/notes/syntax/

amin32
چهارشنبه 21 تیر 1391, 12:55 عصر
یه مشکلی در طراحی EBNF وجود داره.این گرامر رو نگاه کنید:


<program>::=<uses><imports><define><main><functions>
<Uses>::={<Use>{NEWLINE}+}*
<Use>::= <USE_KEY><STRING>


اینجا ما تو خط اول نحو کلی یک برنامه به زبانمون رو بیان کردیم. همونطور که میبینید برناممون با تعریف Use ها شروع میشه ( کتابخانه ها) . بعدش import ها رو داریم و همینطور تا آخر. ولی مشکل از خط دوم شروع میشه. ببینید ما متآسفانه از کاراکتر خط جدید به عنوان کاراکتر هماهنگ کننده ( جدا کننده دستورات ) استفاده کردیم. یعنی بین هر دستور مستقل باید یک یا چند کاراکتر خط جدید وجود داشته باشه (علامت "+" بعد از Newline به همین معنی هست ) . مشکل اینجاست که ممکنه مثلآ برنامه نویس بخواد یه برنامه که فقط از یک دستور فراخوانی کتابخانه (USE) تشکیل شده رو بنویسه و بعد از این دستور هم قاعدتآ نیازی به درج خط جدید نیست. این درحالیه که با توجه به این گرامر , تحلیلگر نحویمون از این برنامه ایراد میگیره.:متفکر:

IamOverlord
چهارشنبه 21 تیر 1391, 15:14 عصر
خوب ببینید می شه از | استفاده کنیم، یعنی اون حالت رو هم داخل خط اول گرامر در نظر بگیریم.
use فقط include می کنه؟ اگه آره، پس بهتره کاری کنیم که use رو بشه در هر قسمتی از کد استفاده کنیم.
ضمنا در این صورت قبل این که این مراحل تحلیل شروع بشه، بهتر نیست که دنبال عبارت های use بگردیم و محتوای فایل مورد نظر رو جایگزین use کنیم؟ یه replace ساده... :متفکر:

amin32
چهارشنبه 21 تیر 1391, 15:44 عصر
خوب ببینید می شه از | استفاده کنیم، یعنی اون حالت رو هم داخل خط اول گرامر در نظر بگیریم.
لطفآ اگه امکانش هست گرامرش رو بنویس. اینطوری نمیشه متوجه شد.



use فقط include می کنه؟ اگه آره، پس بهتره کاری کنیم که use رو بشه در هر قسمتی از کد استفاده کنیم.
به نظرت منطقی تر نیست که کتابخانه ها در ابتدای برنامه معرفی بشن؟


ضمنا در این صورت قبل این که این مراحل تحلیل شروع بشه، بهتر نیست که دنبال عبارت های use بگردیم و محتوای فایل مورد نظر رو جایگزین use کنیم؟ یه replace ساده... :متفکر:
در این مورد باید بعدآ بیشتر تحقیق کنیم. چون این رفتار در مورد ماکروها اتفاق می افته. ولی از این مطمئنم که تا قبل از تحلیل برنامه اصلی نباید در کدهای نوشته شده توسط برنامه نویس دست برد چون ممکنه مثلآ دستور use نوشته شده از نظر نحوی اشباه باشه. از من میپرسی میگم که این کارها باید در مرحله تولید کد میانی انجام بشه.

IamOverlord
چهارشنبه 21 تیر 1391, 18:21 عصر
تا جایی که فهمیدم این دستور use اگه فقط به معنای جایگزینی محتوای فایل باشه، کار قسمت preprocessor هست اصولا... از اون جایی که دستوری مثل if هم در قسمت preprocessor داریم فکر می کنم جرف شما درست باشه، چون این ها هم مثل بقیه ی قسمت های کد نیاز به تحلیل دارند...
اما اگه مثل زبان c مکان زیربرنامه ها نسبت به هم مهمه، فکر می کنم بهتره قابلیت نوشتن use در جاهای مختلف رو بذاریم، چون مثلا ممکنه شما در فایل کتابخانه تون یه زیربرنامه ی B داشته باشید که از زیربرنامه ی A استفاده می کنه و می خواید زیربرنامه ی A رو بعدا در بیرون از فایل کتابخانه تون قبل از دستور use تعریف کنید، یه کارهای دیگه ای مثل استفاده از use لا به لای import ها که در این حالت در فایل کتابخانه مثلا تعدای import پرکاربرد نوشته شده یا ...
به نظرم یه مقدار باید آزادی عمل بدیم.

amir22448
چهارشنبه 21 تیر 1391, 19:22 عصر
من هستم. ولی من نمی دونم چجوری می خوای این کار رو بکنی.به نظر من با زبان C# این کار رو بکنیم بهتره. من که نمی دونم چجوری بسازیم.خیلی سخته. باید اول برای هر کدی که می خوای یه متغیر تعریف کنی و کد خودتو در اون متغیر قرار بدید. ولی همین که به برنامه بفهمونی که این کد چکار می کنه خودش خیلی سخته.:متفکر:.ولی من هستم.با هم درستش می کنیم.

amin32
پنج شنبه 22 تیر 1391, 09:24 صبح
تا جایی که فهمیدم این دستور use اگه فقط به معنای جایگزینی محتوای فایل باشه، کار قسمت preprocessor هست اصولا... از اون جایی که دستوری مثل if هم در قسمت preprocessor داریم فکر می کنم جرف شما درست باشه، چون این ها هم مثل بقیه ی قسمت های کد نیاز به تحلیل دارند...
اما اگه مثل زبان c مکان زیربرنامه ها نسبت به هم مهمه، فکر می کنم بهتره قابلیت نوشتن use در جاهای مختلف رو بذاریم، چون مثلا ممکنه شما در فایل کتابخانه تون یه زیربرنامه ی B داشته باشید که از زیربرنامه ی A استفاده می کنه و می خواید زیربرنامه ی A رو بعدا در بیرون از فایل کتابخانه تون قبل از دستور use تعریف کنید، یه کارهای دیگه ای مثل استفاده از use لا به لای import ها که در این حالت در فایل کتابخانه مثلا تعدای import پرکاربرد نوشته شده یا ...
به نظرم یه مقدار باید آزادی عمل بدیم.

قبل از هر چیز یه توضیح در مورد مسآله اول که عنوان کردی بدم. یک فایل کتابخانه میتونه شامل هزاران خط کد باشه ( و شاید هزاران تابع ) که برنامه نویس نیازی به همه اونها نداره. پس این که بخوایم به ازای هر معرفی کتابخانه , کل کتابخانه رو در کدها جایگزین کنیم یک کار بیهوده هست و باعث پایین آمدن شدید سرعت کامپایل میشه. کاری که باید انجام بشه اینه که برای هر فراخوانی تابع اول باید در توابع تعریف شده در خود برنامه به دنبال اون تابع بگردیم.اگر پیدا نشد در کتابخوانه های معرفی شده به دنبال آن تابع میگردیم. واگر باز هم پیدا نشد باید خطای تابع تعریف نشده رو صادر کنیم.که این اینکارها همگی مربوط به فازهای تحلیلگر معنایی و تولید کد میانی هست. پس بهتره فعلآ بهش فکر نکنیم.
اما اینکه use ها فقط در ابتدای برنامه به کار برده شوند یا در هر جای برنامه ,مربوط میشه به تحلیلگر نحوی و باید همین جا مشخص بشه. راستش با مثالی که زدی من هنوز نتونستم لزوم این که کتابخانه ها در هر جا تعریف بشند رو درک کنم. ببین کتابخونه ها یک فایل مستقل هستند. یعنی هیچ وابستگی به برنامه ای که قراره نوشته بشه ندارند. اگر هم قراره از یک تابع خارجی استفاده کنند , اون تابع در یک کتابخونه دیگه قرار میگیره و در کتابخونه مورد نظر معرفی میشه. دقیقآ مثل کاری که در مورد Include ها انجام میشه. اگر باز هم دلیل قانع کننده ای برای نظرت داشتی در میان بزار.تا در این مورد تصمیم گیری کنیم.
ضمنآ یک نکته هم خدمت دوستانی که فکر میکنند کار ایجاد ساختار لغوی و نحوی یک زبان جدید آسان هست و نیاز به صرف زمان چندانی نداره عرض میکنم. ببینید شما یک کتاب آموزش زبان برنامه نویسی رو در نظر بگیرید. چنین کتابی میتونه حجمی برابر 100 تا 1000 صفحه داشته که قطعآ حداقل 50 درصد اون صرف توضیح ساختار لغوی و نحوی زبان میشه . این در حالیه که تولید ساختار لغوی و نحوی یک زبان جدید به عوامل دیگه ای مثل خلاقیت و در نظر گرفتن موانع پیاده سازی نیازمند هست. شاید جالب باشه بدونید که فقط ابداع ساختار یک زبان جدید که جالب و قابل پیاده سازی باشه هم در علوم کامپیوتر میتونه ارزشمند باشه. و طراحی کامپایلر میتونه ارزش زبان رو به شکل ملموس تری نشون بده.

amin32
سه شنبه 27 تیر 1391, 12:43 عصر
به نظرم فعلآ بهتره به قدرت و انعطاف زبان فکر نکنیم. هر تغییری رو میشه بعدن بهش اضافه کرد. الان باید روی پیاده سازی و مشکلاتی که ممکنه پیش بیاد فکر کنیم. وگرنه اگه بخوایم فقط همینطور روی گسترش زبان فرضیمون کار کنیم به جایی نخواهیم رسید. به نظرم حتی اگه ساده کردن و حذف بعضی قابلیتها میتونه به پیاده سازی کمک کنه, باید اینکار رو انجام بدیم.

amin32
سه شنبه 27 تیر 1391, 12:47 عصر
با توجه به مشغله زیاد خودم باز هم از دوستان دیگه که در زمینه کامپایلر , پارسرها و مباحث مرتبط ( به هر زبانی ) کار کردن دعوت میکنم در پروژه مشارکت کنند.

IamOverlord
شنبه 31 تیر 1391, 16:16 عصر
سلام...
یه مدتیه سرم شلوغه، ولی همچنان سعیم رو می کنم...

خوب، اون گرامری رو که نوشتین این طوری تغییر دادم:

<program>::=<sec_uses_imports><sec_defines>
<sec_defines>::={<define>}
<define>::=<def_global_variables>|<def_procedure_main>|<def_procedure>|<def_function>|<def_structure>|<def_class>
<sec_uses_imports>::={<use_import>}
<use_import>::=<use>|<import>
<use>::=<use_key><file_address>|<use_key><quoted_file_address>
<use_key>::=
<import>::=

البته چون من زیاد وارد نیستم تو زمینه ی نوشتن گرامر، لطفا دوستان همکاری کنند، درستش کنیم. :چشمک:

amin32
شنبه 31 تیر 1391, 19:34 عصر
سلام...
یه مدتیه سرم شلوغه، ولی همچنان سعیم رو می کنم...

خوب، اون گرامری رو که نوشتین این طوری تغییر دادم:

<program>::=<sec_uses_imports><sec_defines>
<sec_defines>::={<define>}
<define>::=<def_global_variables>|<def_procedure_main>|<def_procedure>|<def_function>|<def_structure>|<def_class>
<sec_uses_imports>::={<use_import>}
<use_import>::=<use>|<import>
<use>::=<use_key><file_address>|<use_key><quoted_file_address>
<use_key>::=
<import>::=

البته چون من زیاد وارد نیستم تو زمینه ی نوشتن گرامر، لطفا دوستان همکاری کنند، درستش کنیم. :چشمک:


ببین با توجه به این صفحه:

قسمت define فقط متغیرهای عمومی رو در بر میگیره و توابع و روالها رو شامل نمیشه !
این گرامر داره یک زبان کاملآ متفاوت رو تعریف میکنه!
یک پیشنهادی که بهت میکنم اینه که فعلآ به هیچ وجه قابلیت جدیدی رو به زبان اضافه نکنی.( مثل def_class) . به نظر من پیاده سازی یک زبان خیلی خیلی ساده هم میتونه مشکلات خودش رو داشته باشه. بیخود نیست که تعداد کامپایلرها تقریبآ کم هست و هنوز در بعضی از موارد کمبودهایی وجود داره. پس بهتره فعلآ روی همین قابلیتها کار کنیم.

amin32
شنبه 31 تیر 1391, 20:05 عصر
لازم دیدم کمی در مورد تحلیلگر نحوی و عمکردش توضیح بدم. ببینید ما تا اینجای کار تحلیلگر لغوی رو نوشتیم. کار تحلیلگر لغوی این بود که نوع هر کلمه به کار رفته در کد برنامه رو تشخیص بده و به ازای هر لغت, نوعش رو که به اون توکن گفته میشه رو برای فاز بعدی بفرسته. در پایان این فاز ما علاوه بر کد اصلی برنامه , یک سری توکن رو داریم که نشون میده برنامه نویس انواع مختلف لغات ( عدد صحیح , رشته , کلمه کلیدی , عملگرها و.... ) رو با چه ترتیبی در کنار هم قرار داده که بهش ساختار نحوی برنامه گفته میشه . از طرفی ما به عنوان طراح کامپایلر باید بررسی کنم که این ساختار نحوی از ساختار نحوی زبان ما تبعیت میکنه یا خیر. اینجاست که بحث گرامرها( در اینجا EBNF) مطرح میشه. ما با استفاده از گرامرها و قابلیتهای اون در واقع ساختار نحوی زبان رو توصیف میکنیم. تا با پیاده سازی اون بتونیم این ساختار رو با ساختار کد نوشته شده برنامه نویس مقایسه کنیم و در صورت عدم تطبیق به کاربر هشدار لازم رو بدیم.

amin32
شنبه 31 تیر 1391, 20:13 عصر
همونطور که در اینجا توضیح دادم :
http://barnamenevis.org/showthread.php?296021-%D8%B3%D8%A7%D8%AE%D8%AA-Compiler-%D9%88-%DB%8C%DA%A9-%D8%B2%D8%A8%D8%A7%D9%86-%D8%A8%D8%B1%D9%86%D8%A7%D9%85%D9%87-%D9%86%D9%88%DB%8C%D8%B3%DB%8C-%D8%AC%D8%AF%DB%8C%D8%AF&p=1545873&viewfull=1#post1545873

مشکل ما این هست که از کاراکتر خط جدید به عنوان هماهنگ کننده استفاده کردیم. و این یکم پیاده سازی گرامر رو مشکل کرده. فکر میکنم اگه مثل زبان C ( که از ';' استفاده کرد) و خیلی زبانهای دیگه , ما هم از یک کاراکتر خاص استفاده کنیم , احتمالآ باید این مشکل رفع بشه. البته با همین کاراکتر خط جدید هم غیر ممکن نیست ولی یکمی پیچیده میشه.:متفکر:

IamOverlord
یک شنبه 01 مرداد 1391, 13:12 عصر
ولی مشکل از خط دوم شروع میشه. ببینید ما متآسفانه از کاراکتر خط جدید به عنوان کاراکتر هماهنگ کننده ( جدا کننده دستورات ) استفاده کردیم. یعنی بین هر دستور مستقل باید یک یا چند کاراکتر خط جدید وجود داشته باشه (علامت "+" بعد از Newline به همین معنی هست ) . مشکل اینجاست که ممکنه مثلآ برنامه نویس بخواد یه برنامه که فقط از یک دستور فراخوانی کتابخانه (USE) تشکیل شده رو بنویسه و بعد از این دستور هم قاعدتآ نیازی به درج خط جدید نیست. این درحالیه که با توجه به این گرامر , تحلیلگر نحویمون از این برنامه ایراد میگیره.

یعنی حداقل 1 کاراکتر خط جدید باید در هر کدی وجود داشته باشه؟ در این صورت به نظر من باید قبل از این که کد رو تحویل بدیم، خودمون یه سری ویرایش های جزئی روش بکنیم؛ مثلا به آخر هر کدی یه کاراکتر خط جدید اضافه کنیم...

IamOverlord
یک شنبه 01 مرداد 1391, 13:24 عصر
گرامر BASIC رو تو همون لینکی که گذاشتم (http://rosettacode.org/wiki/BNF_Grammar) نگاه کردم:

<Lines> ::= Integer <Statements> NewLine <Lines>
| Integer <Statements> NewLine
Integer رو که بی خیال، اما بقیش همون مشکلی که ما داریم رو داره، احتمالا اون ها هم یه ویرایش هایی قبل از تحلیل ها انجام می دن... البته برای حل مشکل ببینید این جواب می ده؟:

<Lines> ::= <Statements> NewLine <Lines>
| <LastLineOfCode>
<LastLineOfCode>::= <Statements> NewLine
| <Statements>

amin32
یک شنبه 01 مرداد 1391, 13:38 عصر
یعنی حداقل 1 کاراکتر خط جدید باید در هر کدی وجود داشته باشه؟ در این صورت به نظر من باید قبل از این که کد رو تحویل بدیم، خودمون یه سری ویرایش های جزئی روش بکنیم؛ مثلا به آخر هر کدی یه کاراکتر خط جدید اضافه کنیم...

نه منظورم این نبود که فقط یک کاراکتر خط جدید داشته باشیم. منظورم اینه که کلآ کاراکتر هماهنگ کننده رو تغییر بدیم و یک کاراکتر خاص انتخاب کنیم. در ضمن اینو هم در نظر بگیر که اگه قرار باشه ما به جای برنامه نویس برای هر کد یک کاراکتر خط جدید اضافه کنیم , ممکنه کاربر به اشتباه دو تا دستور رو بدون خط جدید وارد کنه که در اون صورت تشخیصش برای ما خیلی مشکل میشه و پیاده سازی چنین چیزی میتونه خیلی کار رو پیچیده تر کنه.

IamOverlord
یک شنبه 01 مرداد 1391, 13:43 عصر
اون گرامر بالا در مورد چند تا New Line بین 2 خط کد مشکل داره... فکر می کنم این بهتر باشه:

<NL> ::= NewLine <NL>
| NewLine
<Lines> ::= <Statements> <NL> <Lines>
| <LastLineOfCode>
<LastLineOfCode> ::= <Statements> <NL>
| <Statements>

amin32
یک شنبه 01 مرداد 1391, 13:55 عصر
من باز هم پیشنهاد میکنم از یک کاراکتر هماهنگ کننده دیگه استفاده کنیم . یا اصلآ مثل HTML دستورات رو داخل تگها قرار بدیم. در هر دو صورت به راحتی میتونیم مشکل خط جدید رو حل کنیم و فقط کافیه در گرامر بعد از هر دستور به تعداد صفر تا بینهایت خط جدید رو در نظر بگیریم.

IamOverlord
یک شنبه 01 مرداد 1391, 14:37 عصر
ببینید با اون تعریف NL که در آخرین کد گذاشتم اون مشکل تعداد کاراکتر های خط جدید بین دو خط حله... من زیاد با ;... راحت نیستم! پیشنهاد می کنم همین مشکل رو با توجه به گرامر هایی که بقیه نوشتن حل کنیم...

amin32
یک شنبه 01 مرداد 1391, 16:02 عصر
ببینید با اون تعریف NL که در آخرین کد گذاشتم اون مشکل تعداد کاراکتر های خط جدید بین دو خط حله... من زیاد با ;... راحت نیستم! پیشنهاد می کنم همین مشکل رو با توجه به گرامر هایی که بقیه نوشتن حل کنیم...

OK !
با اینکه فکر میکنم استفاده از کاراکتر هماهنگ کننده , ساخت گرامر و پیاده سازی تحلیلگر رو به شدت سادهتر میکنه ولی با راهکارت موافقم.

amin32
یک شنبه 01 مرداد 1391, 16:26 عصر
یک فکر خوب به ذهنم زد:


<program>::=<uses><imports><define><main><functions>
<Uses>::={<Use>}*
<Use>::= <USE_KEY><STRING><Coordinator>
<Coordinator>::={NEWLINE}+|{NEWLINE}* <EOF_key>


مشکل رو با لغت پایان فایل (EOF) حل کردم. Coordinator به عنوان هماهنگ کننده تعریف شده که میتونه " یک یا بیشتر خط جدید باشه" یا میتونه "صفر یا چند خط جدید و یک کاراکتر پایان فایل" باشه. مورد اول برای دستورات میانی هست و مورد دوم برای دستور پایانی که میتونه خط جدید داشته باشه یا نداشته باشه. با این حساب فکر میکنم این مشکل حل شده باشه. فقط باید در تحلیلگر لغوی لغت EOF رو هم به کلمات کلیدی اضافه کنیم.

IamOverlord
یک شنبه 01 مرداد 1391, 18:04 عصر
!===================
! CHARACTER SETS
!===================

{String Char} = {All Valid} - ["]
{ID Tail} = {Alphanumeric} + [_]

!=============
! LITERALS
!=============

StringLiteral = '"' ( {String Char} | '""' )* '"'
ID = {Letter} {ID Tail}*

!==========
! RULES
!==========

<program> ::= <NLOpt> <GlobalStmtList>

<GlobalStmtList> ::= <GlobalStmt> <GlobalStmtList>
|

<GlobalStmt> ::= <UseStmt>
| <ImportStmt>
| <DefineBlock>
| <ProcdureDecl>
| <FunctionDecl>

<UseStmt> ::= 'Use' StringLiteral <NL>

<NL> ::= {NewLine}+|{NewLine}* <EOF_key>

<NLOpt> ::= <NL>
|

<ProcedureDecl> ::= 'Procedure' ID <MethodArgList> <NL> <MethodStmtList> 'End' 'Procedure' <NL>

<FunctionDecl> ::= 'Function' ID <MethodArgList> <Type> <NL> <MethodStmtList> 'End' 'Function' <NL>

amin32
سه شنبه 24 مرداد 1391, 15:31 عصر
دوستان با توجه به مشغله خیلی خیلی زیادی که دارم فکر میکنم دیگه نتونم برای این پروژه وقت بزارم. دوستانی که مایل هستند میتونند پروژه رو ادامه بدند.

کاظم فلاحی خواه
دوشنبه 13 شهریور 1391, 00:57 صبح
راستش منم می خوام ide (ساخت بازی و برنامه برای موبایل)درست کنم که با زبان بیسیک فارسی باشه و کدها رو تبدیل به جاوا کنه بعد با ماشین جاوا برنامه ساخته شده رو اجرا کنه .
دوستان کمکم کنید .

IamOverlord
دوشنبه 13 شهریور 1391, 11:37 صبح
سلام دوست عزیز.
ساخت زبان برنامه نویسی فارسی یه سری مشکلات یا بهتره بگم نکات ریز برای خودم داشت که بی خیالش شدم
به نظرم غربی ها خیلی خوش شانس هستن از نظر ویژگی های زبانشون!
باید به نام گذاری متغیر ها فکر کنید
به بیوند با کتابخانه های خارجی هم همین طور
و مسایل ریز دیگه
مثلا این که باید کد برنامه خوانا باشه
دستورات و عملگر های ریاضی چه جوری باشه
...

l4dl4d
دوشنبه 27 شهریور 1391, 17:27 عصر
دوست عزیز کاظم فلاحی , با سلام
اینکار کار خیلی سختی نیست البته اینجوری:شما یک برنامه ی جاوا که تصاویر پازل یا مثلا اسلاید شو باشه رو تولید کنین
بعد نرم افزاری که مینویسید باید فایل جاوا رو باز کنه و تصاویری که کاربر انتخاب میکنه رو جایگزین کنه
اینجوری براحتی کارتون درست میشه
نرم افزار Fbook هم همچین کاری میکنه

jojoyejojo
سه شنبه 06 اسفند 1392, 22:30 عصر
اکه سرعت براتون مهم نباشه فاز جلو بندی رو میتونید با هر زبانی پیاده سازی کنید ولی احتمالا تو فاز عقب بندی (به خاطر تولید کد ) نمیتونید روی هر زبانی حساب باز کنید.
اگه شما با فازها و زیر فازهای کامپایلر و کاربردشون آشنا نیستید میتونم براتون توضیح بدم. من اطلاعاتم بیشتر در فاز جلوبندی هست. یعنی تا جایی که بتونید یه
مفسر بنویسید.وقتی حرف از کاپایلر میشه معمولا شما باید بتونید برای سیستم عامل مورد نظر یه برنامه اجرایی تولید کنید.که من اطلاعات زیادی در این مورد ندارم. ولی در مفسر شما
فقط فاز جلوبندی و زیر شاخه های اونو دارید.و در آخر کد میانی تولید شده رو مستقیم اجرا میکنید.
در کل فکر میکنم c یا ++c برای ایجاد کامپایلر مناسب باشه. ولی مفسر رو میتونید از هر زبانی استفاده کنید.البته باید به سرعت اجرا دقت کنید.


سلام.من این مطلب شمارو توآرشيو اينجا پيدا کردم و در حال حاضر برای درس کامپايلر بايد ی مفسر ساده بسازم
درواقع سوال استاد اين که ی فايل txt. بديم ب مفسر بعد ی فايل با ی زبان برنامه نويسی تحويل بگيريم که ترجيحا از خانواده C باشه
می خواستم بدونم شما ميتونی کمک کنی؟

smhak16
سه شنبه 05 فروردین 1393, 11:01 صبح
من هستم،من حاضرم که باهم زبان برنامه نویسی جدید بسازیم ولی باید به من میل بدی!

smhak11@gmail.com

brightening-eyes
یک شنبه 01 تیر 1393, 08:41 صبح
بچه ها, چه کاریه,
اینجا (http://llvm.org/)
رو ببینید, یه سری به آموزشاش بزنید, خیلی کارو راحت میکنه

arasahar
چهارشنبه 04 تیر 1393, 00:12 صبح
سلام دوستان هم وطن اگه پول درست حسابی تو کار هست من هستم چون هم علمش و هم حوصله اش را دارم من به عنوان یه نیمچه استاد ایرانی تو کشور خودم کسی نیست که بهمون بها بده ولی از سایر جاها بهم خیلی پیام میدن و اومدهاند به شهرمون و منو دیده اند و خواسته اند که با اونها کار کنم البته پس از امتحان اینو خواسته اند نه الکی من هم چون به پول نیاز دارم فکر میکنن که با اونها میرم ولی تا حالا استقامت کردهام پس اگه پول بدین میتونم باهاتون کار بکنم ببخشین ولی
آنچه شیران را کند روبه مزاج
احتیاج است احتیاج

arasahar
چهارشنبه 04 تیر 1393, 00:15 صبح
my mail is
hacando60@gmail.com
please if u willl please call
thanks a lotttttttttttttttttttttttttttt

one2015
شنبه 20 تیر 1394, 13:07 عصر
سلام.
من می خوام برای زبان -c کامپایلر طراحی کنم.فاز scanner ,parser , semantic analyser نوشتم و درست کار میکنه این فازو نوشتم وقتی فایلهای خروجی رو کامپایل میکنم تا قبل از تابع yyparse() کار میکنه ولی بقیه اش تو console چاپ نمیشه یعنی خروجی نمیده لطفا کمک کنید.

mak12776
دوشنبه 06 آبان 1398, 01:45 صبح
سلام.
من داشتم توی گوگل "برنامه نویسی open source" رو جستجو می کردم، که به این انجمن رسیدم و بعدا شانسی این پست رو پیدا کردم.

من پست آقای lamOverlord رو در اینجا (https://barnamenevis.org/showthread.php?360400-%DB%8C%D8%A7-%D8%A8%DB%8C-%D8%AE%DB%8C%D8%A7%D9%84-VB6-%D8%A8%D8%B4%DB%8C%D8%AF-%DB%8C%D8%A7) خوندم که در مورد نوشتن یه نسخته جدید از VB نوشته بودند. و بیشتر بخش های این پست رو هم خوندم.

آقا منم هستم. اصلا خودم دارم سعی می کنم به زبان برنامه نویسی جدید بسازم به اسم Rest. سینتکسی (syntax) که برای Rest در نظر گرفتم می شه گفت تقریبا چیزی شبیه به VB هست. ولی من اصلا VB رو کار نکرده بودم و سینکس رو تاحالا ندیده بودم. و چیزی که من می خواستم بسازم یه ورژن دیگه از python بود که به C یا Assembly تبدیل بشه. من مشکلی که داشتم این بود که نوشتن برنامه توی C سخت بود چون که هی باید سمی کلن می زاشتم و حافظه برنامه رو به صورت دستی free و allocate می کردم. و نوشتن برنامه توی python راحت تره، ولی زمان اجرای برنامه بیشتر می شه. و برنامه بهینه نیست اصلا. کاری که من می خواستم بکنم این بود که یه زبان برنامه نویسی بسازم که سینتکسش در حد پایتون ساده باشه و به C تبدیل بشه و تمام بهینه سازی های لازم رو انجام بده.

البته سینکسی که در نظر گرفتم از python راحت تره و دیگه مثل پایتون لازم نیست که همه جملات داخل یه بلاک با یه tab جلو بره، به جاش آخر هر بلاک یه end اضافه می کنیم. مثلا اگه تعریف کردن function توی python این شکلی باشه:


def sum(a, b):
return a + b

چیزی که توی Rest در نظر گرفته بودم اینه:


def sum(a, b)
return a + b
end


چندین تا زبان برنامه نویسی دیگه هم با سینتکس های ساده تر داره ساخته می شه، وجود دارند که اینا هستن: vlang (https://vlang.io/), nim (https://nim-lang.org/) و crystal (https://crystal-lang.org/)

nim تا یه حد خیلی زیادی جلو رفته و یه کتاب هم برای آموزشش نوشته شده، و به زبان C و javascript هم تبدیل می شه. ولی بهینه نمی شه. یا می شه گفت یه سری قابلیت براش در نظر گرفتن برای بهینه سازی، ولی بهینه سازی حداکثر رو انجام نمی ده. و می تونم بگم که می شه زبان برنامه نویسی نوشت که خیلی بهینه تر باشه.

crystal هم سینتکس خیلی ساده ای داره و مثل Ruby می مونه و به native byte code تبدیل می شه. سینتکسش (https://crystal-lang.org/reference/syntax_and_semantics/if.html) رو هم یه نگاهی بکنید، بدک نیست.

vlang رو زیاد نخوندم در موردش ولی خیلی بهینه شده کامپایل می شه. و سینکس خیلی راحتی نداره.

ولی طرحی که من برای نوشتن Rest در نظر گرفتم، یه جوری در برگیرنده بیشتر ویژگی های زبان های برنامه نویسی بالا هست. یا شاید بشه گفت هر ویزگی که به نظرم خوب اومده رو توی نوشتن Rest در نظر گرفتم. البته در بعضی از قسمت هاش هنوز شک دارم، یا نوشتن بعضی از ایده ها خیلی وقت گیر خواهد بود. اما هنوز اول کارم، توی نوشتن مرحله Tokenizer ام. نمی دونم شما بهش می گید مترجم معنوی یا لغوی، ولی اینجا (http://www.cs.man.ac.uk/~pjj/farrell/comp3.html) می تونید پیدا کنید که منظورم چی هست.

نمی دونم که می تونیم باهم هم کاری داشته باشیم یا نه، یا اصلا اسم زبانی که می خوایم بسازیم رو، چی بزاریم. ولی من آماده همکاری هستم اگه ایده و نظری دارید بگید که با هم گفت و گو کنیم. و در ضمن اسم Rest رو برای این انتخاب کردم که انگاری که استراحت برنامه نویس ها باشه. بشه توی یه سینتکس ساده برنامه نویسی کرد و به بهترین شکل ممکن بهینه بشه. :متفکر: البته هنوز ایده است تا به پروژه کامل برسه. :چشمک:

اینجا (https://github.com/mak12776/rest) می تونید سورس Rest رو که دارم می نویسم ببنید. و اینجا (https://github.com/mak12776/rest/blob/master/texts/design) هم می تونید طرحی که در نظر گرفتم رو ببنید. اگه چیزی رو متوجه نشدید بگید که توضیح بدم.

و یه پیشنهاد دارم توی پست هاتون رو که می خوندم:
بین FASM و MASM شک داشتید که به کدوم کامپایل بشه، به نظر من به NASM (https://www.nasm.us/) کامپایل بشه بهتره. چون که اولا NASM خیلی معروف تره و افراد بیشتری روش کار کردند و open source هم هست، و هم به خاطر این که هم برای ویندوز و هم برای لینوکس کامپایل می کنه. ولی MASM برای لینوکس کامپایل نمی کنه، open source هم نیست و FASM هم به اندازه NASM پیشرفته نیست. یه اسمبلر دیگه هم وجود داره به اسمه GAS که وقتی C یا Cpp می خود کامپایل بشه به اون تبدیل می شه، ولی اصلا راحت نیست و بیشتر برای C ساخته شده. یه راه حل دیگه هم وجود داره اونم اینه که از library هایی که برای تولید byte code استفاده می شه، بهره ببرید که بستگی به این داره که با کدوم راحت تر باشید.

منتظر نظرتون هستم.