برنامه نويسی در دات نت

دات نت محيطی جديد بمنظور طراحی، پياده سازی و اجرای برنامه های کامپيوتری را در اختيار طراحان و پياده کنندگان نرم افزار قرار می دهد. با استفاده از پلات فرم فوق ، می توان بسرعت اقدام به پياده سازی نرم افزار نمود.

برنامه های توليده شده ، امکان استفاده از پتانسيل های محيط
( Common Language Runtime CLR ) را خواهند داشت . آشنائی با مفاهيم اوليه برنامه نويسی در محيط فوق ، دارای اهميت خاص خود بوده و سرعت در استفاده مطلوب از محيط فوق ، را بدنبال خواهد داشت . در مقالاتی که در اين زمينه ارائه خواهد شد به بررسی مفاهيم اوليه برنامه نويسی محيط فوق ، خواهيم پرداخت . در اين راستا ، در ابتدا با نحوه نوشتن يک برنامه آشنا و در ادامه به تشريح برخی از مفاهيم مهم در اين زمينه ، خواهيم پرداخت .
نوشتن يک برنامه در فريمورک دات نت

تمامی زبانهای حمايت شده در دات نت ، از سيستم نوع يکسان ، کتابخانه کلا س فريمورک مشابه و CLR استفاده خواهند کرد . بدين ترتيب، تمامی برنامه های نوشته شده با يکی از زبانهای حمايت شده ، خصايص مشابهی را به اشتراک می گذارند. شايد مهمترين تفاوت قابل توجه در رابطه با زبان های برنامه نويسی حمايت شده در دات نت ، به گرامر هر يک از آنها برگردد . ( در مثال هائی که در اين مقاله ذکر می گردد ، از ويرايشگر Notepad ،در مقابل ويژوال استوديو دات نت، استفاده شده است . مثال های ارائه شده به اندازه کافی ساده بوده تا بتوان بکمک آنان با فرآيندهای ترجمه و اجراء ، بسرعت آشنا گرديد ).
نوشتن يک برنامه

برای نوشتن يک برنامه ساده در دات نت ، مراحل زير را دنبال می نمائيم :
• فاز اول : ايجاد برنامه
برنامه Notepad را فعال و پس از درج کدهای زير آن را با نام Hello.vb ، ذخيره نمائيد .
يک برنامه نمونه نوشته شده به زبان VB.NET
Imports System

Public Class MainApp
Public Shared Sub Main( )
Console.WriteLine( “Welcome to .NET Programming ” )

End Sub
End Class
• فاز دوم : ترجمه و ايجاد يک فايل اجرائی
برای اجراء برنامه ايجاد شده در مرحله قبل ، در ابتدا کمپايلر VB.NET را از طريق خط دستور و بصورت زير فعال می نمائيم : ( دستور فوق را می توان از طريق خط دستور ويندوز و يا خط دستور موجود در ويژوال استوديو ، فعال کرد )
vbc Hello.vb

در ادامه و پس از ايجاد فايل اجرائی (hello.exe ) ، امکان اجرای برنامه فراهم می گردد.

استفاده از Namespace

با استفاده از VB.NET ، می توان به کلاس ها مراجعه و از آنان استفاده کرد . در مثال زير ، يک نمونه از کلاس System.Io.FileStream ، ايجاد شده است .
Dim aFileStream As System.IO.Filestream
مراجعه به Namespace های مورد نياز در يک برنامه روشی مناسبتر در اين زمينه است . با استفاده از namespace ، ضرورتی به توصيف تمامی مراجعات به کتابخاته کلاس ، وجود نخواهد داشت .

Imports System.IO
…..
Dim aFileStream As Filestream
مثلا” برای دستيابی به اشياء System ، می بايست از Namespace با نام System در برنامه استفاده گردد. ( Imports) .
تعريف namespace و کلاس
VB.NET ، امکانات حمايتی لازم در خصوص ايجاد Namespace های خاص و کلاس های مربوط به آن را ارائه می نمايد. (نکته : مدل زير يک روش عمومی برای نامگذاری namespace است ) :

CompanyName.TechnologyName
.For Example:
Microsoft.Office
namespace در VB.NET
در VB.NET با استفاده از عبارت namespace می توان يک namespace را تعريف کرد . با استفاده از namespace تعريف شده ، امکان کپسوله نمودن کلاس های ايجاد شده ، فراهم خواهد شد.
Namespace CompVB
Public Class StringComponent
….
End Class
End Namespace
برخی از ويژگی های namespace عبارتند از :
• namespace می تواند درون ساير namespace ها ، مستقر گردند .
• يک namespace می تواند در چندين فايل تعريف گردد .
• يک فايل حاوی کد مبداء می تواند چندين namespace را تعريف نمايد.
نقاط ورود ، حوزه ، تعاريف
هر برنامه اجرائی می بايست شامل يک نقطه ورود خارجی باشد . مکان فوق ، محلی را که برنامه اجرای خود را از آنجا آغاز می نمايد ، مشخص می نمايد..در VB.NET تمامی کد می بايست در متدهای يک کلاس قرار بگيرد.
نقاط ورود در VB.NET
بمنظور ارائه کد نقطه ورود در VB.NET ، در ابتدا می بايست يک ماژول و يا يک کلاس مشخص گردد .
Public Module modMain

Public Class clsMain
در ادامه می بايست نقطه ورود برای برنامه ، مشخص گردد. نقطه ورود ، می بايست بعنوان يک متد عمومی که main ناميده می شود ، در نظر گرفته شود.( کمپايلر به دانش فوق نياز خواهد داشت ) . در يک کلاس ، متد فوق می بايست بصورت اشتراکی تعريف گردد .امکان تعريف متد فوق در يک ماژول بصورت اشتراکی ، وجود نخواهد داشت . نحوه تعريف ( مشخص نمودن ) نقاط ورود برای يک ماژول و يا يک کلاس ، بصورت زير است :
Public Module modMain
Public Sub Main( )

End Sub
End Module

Public Class clsMain
Public Shared Sub Main( )

End Sub
End Class
حوزه
VB.NET ، از نقطه بعنوان يک عملگر resolution حوزه ، استفاده می نمايد . مثلا” در صورت استفاده از متد WriteLine مربوط به کلاس Console ، از گرامر Console.WriteLine ، استفاده می شود.
تعاريف
در VB.NET ، الزامی به تعريف يک متغير قبل از استفاده از آن نمی باشد . پيشنهاد می گردد که در چنين مواردی متغيرها با صراحت تعريف گردند. در اين راستا می توان از عبارت options ، استفاده کرد. بمنظور ايجاد نمونه ای از يک شی ، از New استفاده می گردد. مثال زير ، نحوه تعريف يک شی از نوع Comp در namespace با نام Lib و با نام MyComp را نشان می دهد .
Dim myComp As New Lib.Comp( )

کنسول ورودی و خروجی
می توان از کلاس Console ، مربوط به CLR وابسته به System Namespace ، برای ورودی و خروجی هر نوع رشته و مقادير عددی توسط متدهای Read , ReadLine و Write,WriteLine استفاده کرد . برنامه زير، نحوه نمايش يک رشته در خروجی را نشان می دهد .
برنامه نمونه :
Imports System

Public Class MainApp
Public Shared Sub Main( )
Console.WriteLine( “Welcome to .NET Programming ” )
End Sub

End Class
ترجمه و اجراء يک برنامه فريمورک دات نت
اکثر جنبه های برنامه نويسی در دات نت برای تمامی زبانهای سازگار ، يکسان است . هر کمپايلر حمايت شده باعث توليد کدهای “خود تشريح ” MSIL)Microsoft Intermediate Language) ، می گردد . تمامی کدهای مديريت يافته ( Managed code ) با استفاده از CLR(Common Language runtime) ، اجراء خواهند شد . CLR ، امکان يکپارچگی بين برنامه ها ، مديريت اتوماتيک حافظه ، برخورد يکدست با موارد خاص و استثناء ، امنيت پيشرفته و در نهايت يک مدل برنامه نويسی ساده و همگن را ارائه می نمايد.
گزينه های کمپايلر

فريمورک دات نت، دارای يک کمپايلر خط دستوری برای VB.NET است ( vbc.exe ) . برای ترجمه برنامه Hello.vb ، بکمک کمپايلر فوق ، از دستور زير استفاده می شود :
vbc Hello.vb

گرامر فوق، باعث فراخوانی کمپايلر VB.NET می گردد. در اين مثال خاص، صرفا” نام فايل مورد نظر برای کمپايلر مشخص شده و در ادامه ، کمپايلر فايل اجرائی را توليد خواهد کرد ( Hello.exe )
گزينه های خط دستور
در VB.NET ، می توان ليست کاملی از گزينه های همراه کمپايلر را با استفاده از ?/ ، مشاهده نمود ( ?/ Vbc ) . از گزينه های مفيد در اين زمينه، می توان به سوئيچ out/ ، ( نام فايل خروجی را مشخص می نمايد) و سوئيچ target/ ، ( نوع کد مقصد را مشخص می نمايد”) ، اشاره کرد. بصورت پيش فرض ، نام فايل خروجی مشابه نام فايل ورودی و با انشعاب exe . ، خواهد بود. مقدار پيش فرض برای تعيين نوع کد مقصد ، يک برنامه اجرائی است ( سوئيچ t/ ، دارای عملکردی معادل با سوئيچ target/ است ). دستور زير نحوه استفاده از سوئيچ های فوق را نشان می دهد :

vbc /out :hello.exe /t:exe hello.vb
استفاده از گزينه کمپايل reference/
در زمان مراجعه به ساير اسمبلی ها ، می بايست از سوئيچ reference/ ، استفاده گردد . گزينه فوق اين امکان را برای کمپايلر فراهم می آورد که اطلاعاتی را ايجاد و در کتابخانه های مشخص شده استقرار تا زمينه استفاده از آنان برای کد مورد نظر ( در حال ترجمه ) ، فراهم گردد. مثال زير نحوه ايجاد يک برنامه اجرائی از طريق خط دستور و با استفاده از reference / ، را نشان می دهد .
( عملکرد سوئيچ r / مشابه reference / است ).

Vbc / r:assembll.dll , assemb2.dll / out :output.exe input.vb
در بخش دوم اين مقاله به بررسی فرآيند اجراء مديريت يافته ( اداره شده ) ، خواهيم پرداخت .

مفاهيم اوليه برنامه نويسی در دات نت ( بخش دوم )
در بخش اول اين مقاله به بررسی يک برنامه نمونه ساده دات نت پرداخته شد و از اين رهگذر با برخی مفاهيم اوليه و در عين حال مهم برنامه نويسی در دات نت آشنا شديم . در بخش دوم اين مقاله به بررسی فرآيند اجراء پرداخته و بدنبال آن با برخی ديگر از مفاهيم اساسی برنامه نويسی در دات نت آشنا خواهيم شد .
در فريمورک دات نت ، CLR زير ساخت لازم برای يک محيط اجراء مديريت يافته ( اداره شده ) را فراهم می نمايد . در زمان پياده سازی يک برنامه در فريمورک دات نت ، برنامه مورد نظر می تواند با استفاده از هر يک از زبان های سازگار با CLR ، نوشته گردد. کمپايلر استفاده شده ، کدها را به مقصد CLR ، ترجمه می نمايد . پس از فرآيند ترجمه کد نوشته شده ، يک ماژول مديريت يافته( اداره شده ) ايجاد خواهد شد. ماژول فوق، در فايلی که PE)Portable Executable) ، ناميده می شود، قرار گرفته و شامل اطلاعات زير خواهد بود :

• MSIL)Microsoft Intermediate Language) ، کمپايلر کد نوشته شده را به MSIL ترجمه می نمايد . کد فوق ، مجموعه ای از دستورالعمل های مستقل از نوع پردازنده بوده و در ادامه با توجه به نوع پردازشگر به کدهای مختص ماشين تبديل می گردند.

• Type metadata .اطلاعات فوق ، نوع ها ، اعضاء و ساير مراجع استفاده شده توسط CLR در زمان اجراء را بطور کامل تشريح خواهد کرد.
• مجموعه ای از ساير منابع . منابع فوق ، شامل موارد متععدی نظير فايل های Jpg . و يا Bmp . ، می باشند .

اگر در زمان استفاده از کمپايلر ويژوال بيسيک از سوئيچ target / ، استفاده و مقدار آن Exe و يا Library در نظر گرفته شود ، کمپايلر يک ماژول اجرائی را توليد که يک اسمبلی (Assembly ) خواهد بود. اسمبلی ها بخش ضروری و اساسی برنامه نويسی در فريمورک دات نت بوده و CLR از آنان بعنوان واحدهای پايه و بمنظور اشتراک ، بکارگيری امنيت و ورژن های متفاوت، استفاده می نمايد. CLR دات نت ، صرفا” کدهای MSIL را که در يک اسمبلی موجود می باشند ، اجراء خواهد کرد . در صورتيکه بهمراه سوئيچ target / (در کمپايلر ويژوال بيسيک ) ، از Module استفاده شود ، کمپايلر يک ماژول مديريت يافته را توليد که يک

اسمبلی نخواهد بود .ماژول توليده شده ، شامل يک مانيفست نبوده و نمی تواند توسط CLR ، اجراء گردد. يک ماژول مديريت يافته را می توان به يک اسمبلی و از طريق استفاده از کمپايلر ويژوال بيسيک و يا با استفاده از Assembly Linker) Al.exe) اضافه نمود. در ادامه به تشريح MSIL ، متاديتا و اسمبلی خواهيم پرداخت .

کد اجرائی
در زمان اجرای يک برنامه مديريت يافته ، لودر سيستم عامل ، CLR را در حافظه مستقر و در ادامه زمينه اجرای کد MSIL ماژول های مديريت يافته ، فراهم می گردد. با توجه به اينکه پردازنده ميزبان در مقطع کنونی ، قادر به اجرای مستقيم دستورالعمل های MSIL نخواهد بود، CLR ، می بايست در ابتدا دستورالعمل های MSIL را به کد مختص ماشين و با توجه به نوع پردازنده ، تبديل نمايد .

CLR ، تمام کدهای MSIL را به دستورالعمل های مستقل از پردازنده در زمان لود ، ترجمه نخواهد کرد . در مقابل، CLR در زمان فراخوانی هر يک از توابع ، دستورالعمل های مربوطه را به کد مختص پردازنده تبديل خواهد کرد.MSIL ، صرفا” در زمان مورد نياز، ترجمه خواهد شد . عناصر CLR که مسئوليت انجام عمليات فوق را برعهده دارند، کمپايلر JIT)Just in Time) ، ناميده می شود . ترجمه JIT ، باعث صرفه جوئی حافظه و زمان در حين مقداردهی اوليه برنامه می گردد .

Appliaction Domain
سيستم عامل و محيط های اجراء نوع های خاصی از ايزولاسيون ( تمايز) بين برنامه ها را ارائه می نمايند . با ارائه سرويس فوق ، اين اطمينان بوجود خواهد آمد که يک برنامه در حال اجراء قادر به تاثير منفی بر ساير برنامه ها ی غير مرتبط ، نخواهد بود . ويژگی فوق ، يک واحد ايمن و چندکاره پردازش را ارائه نموده و CLR بر اساس آن قادر به ايزولاسيون بين برنامه ها خواهد بود. حوزه های برنامه ، عموما” توسط ميزبانان زمان اجراء که مسئوليت فعال نمودن CLR قبل از اجرای برنامه ها را برعهده دارند ، فراهم می گردد.

متاديتا
هر کمپايلر که مقصد آن CLR است ، نيازمند توزيع ( انتشار) کامل متاديتا در هر يک از ماژول های مديريت يافته است .متا ديتا ، مجموعه ای از جداول داده بوده که بصورت کامل هر يک از عناصر تعريف شده در يک ماژول را تشريح می نمايد .اطلاعات فوق ، شامل نوع داده ، اعضاء بهمراه تعاريف مربوطه ، پياده سازی و مراجعه به ساير نوع ها و اعضاء باشد . متاديتا ، تمامی اطلاعات موردنيازبرای ارتباط عناصر نرم افزاری توليده شده را در اختيار CLR قرار خواهد داد .رويکرد فوق ، جايگزينی مناسب برای تمامی تکنولوژی های قديمی نظير: IDL)Interface Defination Language) ، کتابخانه های نوع و ثبت خارجی ( External registration ) ، می باشد. متا ديتا همواره در يک فايل exe . و يا dll . ، حضور داشته و شامل کد MSIL است . بنابراين ، امکان تفکيک متاديتا از کد MSIL وجود نخواهد داشت .با توجه به اينکه متاديتا در يک مستقل از يک زبان برنامه نويسی خاص بوده و در يک محل مرکزی نظير ريجستری ويندوز ذخيره نمی شوند ، امکان تشريح اتوماتيک برنامه های دات نت ، فراهم می گردد.

متاديتا دارای کاربردهای متعددی است که مهمترين آنها عبارتند از :
• مکان يابی و لود کلاس ها . با توجه به اينکه متا ديتا و MSIL در يک فايل مشابه قرار دارند ، تمام اطلاعات موجود در اين فايل برای CLR ، در زمان ترجمه قابل استفاده بوده و ضرورتی به استفاده از فايل های هدر(header) وجود نخواهد داشت ( تمام نوع ها در هر اسمبلی توسط مانيفست مربوطه اسمبلی ، تشريح می گردند ).

• تاکيد امنيت . متا ديتا ، می تواند شامل مجوزهای لازم بمنظور اجراء کد باشد ( البته عکس عبارت فوق نيز ممکن است وجود داشته باشد ، يعنی متا ديتا می تواند شامل مجوزهای لازم بمنظور اجراء کد نباشد ) . سيستم امنيتی از مجوزها استفاده تا باعث ممانعت کد از دستيابی به منابعی گردد که مجوز لازم برای دستيابی به آنان وجود ندارد
MSIL

MSIL مايکروسافت که در برخی حالات Managed code ناميده می شود ، دستورالعمل هایی می باشند کمپايلرآنها را در زمان ترجمه کد اوليه ، توليد می نمايد. صرفنظر از سازماندهی منطقی آنان ، اکثر اسمبلی ها شامل کدهائی با فرمت MSIL می باشند . MSIL يک زبان ماشين مستقل از پردازنده بوده که توسط مايکروسافت و مشاوره با ساير توليدکنندگان کمپايلر، ايجاد شده است . MSIL يک زبان بمراتب سطح بالاتر نسبت به اکثر زبان های ماشين است . MSIL شامل دستورالعمل های لازم برای عمليات متداولی نظير : دستوراتی برای ايجاد ، مقداردهی و صدا زدن متدهای مربوط به يک شی ( اشياء ) ، دستورات لازم برای عمليات منطقی جاری ، Control Flow ,DMA و Exception handling می باشد .

قبل از اينکه کد MSIL قادر به اجراء گردد ، می بايست به کد مختص يک پردازنده خاص توسط يک کمپايلر JIT ، تبديل گردد. CLR ، يک کمپايلر JIT با معماری خاص برای هر نوع معماری پردازنده ، ارائه می نمايد . کمپايلرهای JIT مبتنی بر يک معماری خاص ، امکان نوشتن کد مديريت يافته را فراهم تا در ادامه و بکمک آن امکان ترجمه و توليد کد وابسته به يک معماری خاص فراهم و در نهايت زمينه اجراء کد نوشته شده ، فراهم گردد.(هر کد مديريت يافته که API مختص يک سيستم عامل و يا کتابخانه ها را استفاده می نمايد ، صرفا” قادر به اجراء بر روی سيستم های عامل خاصی خواهد بود ) .
اسمبلی ها
يکی ديگر از عملياتی که CLR ، انجام می دهد لود و اجرای برنامه های دات نت است . برنامه های دات نت بعنوان اسمبلی بکار گرفته می شوند . اسمبلی شامل يک و يا چندين فايل EXE و يا DLL بهمراه اطلاعات متا ديتا است . متا ديتا مربوط به تمام اسمبلی در مانيفست اسمبلی ذخيره می گردد . CLR ، از اسمبلی بعنوان واحدهای عملياتی جهت اشتراک و استفاده مجدد استفاده می نمايد. يک اسمبلی ، واحد بکارگيری کلاس است ( در مقايسه با يک Dll منطقی ) هر اسمبلی شامل تمامی فايل های فيزيکی است که واحد اجرائی ( عملياتی ) را تشکيل خواهد داد ( ماژول مديريت يافته ، منابع ، فايل های داده ) . از لحاظ مفهومی ، اسمبلی ، روشی را بمنظور مشاهده مجموعه ای از فايل ها بعنوان يک موجوديت ، فراهم می نمايد. استفاده از اسمبلی ها بمنظور ايجاد يک برنامه ، يک بايد است . در اين راستا می توان ، نحوه بسته بندی اسمبلی ها بمنظور استفاده را انتخاب کرد.
مانيفيست اسمبلی ( Assembly Manifest )
يک اسمبلی شامل بلاکی از داده ها است که “مانيفست ” ، ناميده می شود . مانيفست ، جدولی است که هر entry آن نام يک فايل بوده و بعنوان بخشی از اسمبلی در نظر گرفته خواهد شد.مانيفست شامل متا ديتا ئی است که بمنظور مشخص نمودن ملزومات ورژن ، يکسان سازی امنيت ، و ساير اطلاعاتی مورد نيازی است که از آنان بمنظور تعريف حوزه اسمبلی و مراجع لازم بمنظور دستيابی و استفاده از منابع ها و کلاس ها ، استفاده می گردد. با توجه به اينکه متاديتا باعث می شود که يک اسمبلی دارای ويژگی خود تشريحی گردد ، CLR همواره دارای اطلاعات مورد نياز در رابطه با اسمبلی بمنظور اجراء آن خواهد بود . تمامی برنامه ها که توسط CLR اجراء می گردند ، می بايست ترکيبی از يک و يا چندين اسمبلی باشند . تمام فايل هائی که يک اسمبلی را ايجاد می نمايند در مانيفست اسمبلی ليست می گردند . مانيفست ، قادر به ذخيره شدن در يک و يا چندين فايل است:
• اسمبلی های تک فايل ( Single-file) . اگر اسمبلی صرفا” دارای يک فايل مرتبط باشد ، مانيفست همرا ه و مرتبط با فايل PE ، خواهد بود .
• اسمبلی های چند فايل ( Multi-file ) ، اگر اسمبلی دارای بيش از يک فايل مرتبط باشد ، مانيفست می تواند بصورت يک فايل stand alone بوده و يا در يکی از فايل های PE در اسمبلی مستقر گردد.
ابزارهای CLR
CLR ، در رابطه با تست و اشکال زدائی کد MSIL دو ابزار را ارائه می نمايد:
• اسمبلر MSIL . اسمبلر MSIL ( فايل ILasm.exe ) کد MSIL را بعنوان ورودی اخذ و يک فايل PE شامل نمايش باينری کد MSIL بهمراه متا ديتا مورد نياز را توليد می نمايد . گرامر استفاده بصورت زير است:
ILasm [options] filename [options]
• برنامه MSIL Disassembler . با استفاده از برنامه فوق ( فايل ILdasm.exe ) می توان بررسی لازم در خصوص متديتا و کد disassembled هر يک از ماژول های مديريت يافته را انجام داد .