loading...
دانلود سرای دانشجویی

پايگاه داده XML

يک پايگاه داده XML سيستم نرم افزاری است که اجازه می دهد داده در فرمت XML وارد، پردازش و ارسال شود.

دو دسته اصلی پايگاه داده XML وجود دارد:

1. XML-enabled . پايگاه داده ای که مستند XML را به عنوان ورودی گرفته به يک پايگاه داده ديگر نظير رابطه ای تبديل می کند و پس از انجام عمليات آنرا مجددا به XML بر می گردند.
2. Native XML (NXD). مدل داخلی چنين پايگاه داده ای بر پايه XML است و مستندات XML را به عنوان منبع ذخيره سازی مستقيما استفاده می کند.

دليل استفاده XML در پايگاه داده شفافيت داده است. داده از پايگاه داده استخراج می شود و در مستندات XML قرار می گيرد و برعکس. به اين صورت هزينه ذخيره داده در فرمت XML هم کمتر می شود.

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

عناصر مدل داده
انواع مدل های داده
مدل سلسله مراتبی
مدل شبکه ای
پايگاه داده XML


مدل کردن داده (data modeling) تحلیل و توصيف داده های محیط عملیاتی و ارتباط بین آنها و شرح معنی و قیدهای داده است.

یک مدل داده قالب قراردادی برای ساخت و کارکردن با داده دراختیار می گذارد.

يک مدل داده پديده های دنيای واقعی را توصيف می کند و ساختار داده مورد نیاز برای حل مسئله خاص و ارتباط درونی بین ساختارها را تعریف می کند. دیاگرام ER مثالی از این نوع است که بیشتر توسط طراحان و تحلیل گران سیستم به کار می رود.

علاوه براين مدل داده تعیین می کند یک DBMS چگونه داده را درون خود، به کاربران و برنامه های کاربردی نمایش دهد. مدل رابطه ای مثالی برای این نوع از مدل داده است.

هر رويدادی که باعث شود CPU اجرای عادی يک برنامه را قطع کند وقفه ناميده می شود. يک برنامه نويس اسمبلی با صدور وقفه های نرم افزاری می تواند به طور موثری با دستگاه های جانبی ارتباط برقرار کند.

انواع وقفه
INT
جدول بردار وقفه
چند نمونه وقفه متعارف


گاهی اوقات جريان عادی اجرای يک برنامه برای پردازش رويدادی که نياز به پاسخ سريع دارد متوقف می شود. سخت افزار کامپيوتر برای مديريت اين رويدادها مکانيسمی به نام وقفه (interrupt) را دارد.

مثال. وقتی mouse حرکت می کند، سخت افزار mouse برنامه جاری را متوقف می کند تا حرکت mouse گرفته شود( برای حرکت مکان نمای mouse روی صفحه نمايش).

وقتی CPU يک سيگنال وقفه را تشخيص می دهد، فعاليت جاری خود را متوقف می کند و روتين خاصی را فراخوانی می کند که روتين وقفه (interrupt handler) نام دارد. اين روتين علت وقوع وقفه را تشخيص می دهد و عکس العمل مناسب را انجام می دهد.

بيشتر روتين های وقفه بعد از پايان يافتن کنترل اجرا را به برنامه متوقف شده بازمی گردانند. آنها کليه مقادير ثبات ها را به وضعيت قبل از توليد وقفه بر می گردانند. بنابراين برنامه متوقف شده به گونه ای به اجرا ادامه می دهد که هيچ اتفاقی نيافتاده است به جز اين که سيکل های CPU را از دست می دهند.

وقتی دو يا چند وقفه همزمان با هم اتفاق می افتند، CPU از سيستم الويت استفاده می کند و می تواند در طی اجرای بخش بحرانی يک برنامه وقفه ها را غيرفعال کند. وقتی دارد يک روتين وقفه را اجرا می کند کليه وقفه های با الويت کمتر يا، تا زمان خاتمه اجرای روتين، غير فعال هستند.


انواع وقفه

256 سطح الويت توسط پردازنده های 80x86 پشتيبانی می شود که می توان آنها را به سه گروه کلی تقسيم کرد:

• وقفه های داخلی سخت افزاری
• وقفه های خارجی سخت افزاری
• وقفه های نرم افزاری

وقفه های داخلی سخت افزاری

وقفه های داخلی سخت افزاری (internal hardware-interrupts) بدليل رخ دادن وضعيت معينی که درحين اجرای يک برنامه پيش آمده توليد می شوند(مانند تقسيم بر صفر).

وقفه هايی که در اثر خطا بوجود می آيد تله (trap) هم ناميده می شود. تله باعث سقط برنامه می شوند.

اين وقفه ها توسط سخت افزار اداره می شوند و امکان تغيير آنها وجود ندارد. اما با وجوديکه نمی توان آنها را مستقيما مديريت کرد، اين امکان وجود دارد که از اثر آن روی کامپيوتر به نحو مفيدی استفاده شود.

مثال. سخت افزار وقفه شمارنده ساعت کامپيوتر را چندبار در ثانيه فراخوانی می کند تا زمان را نگه دارد. می توان برنامه ای نوشت که مقدار شمارنده ساعت را خوانده آنرا به شکل قابل درک کاربر به صورت ساعت و دقيقه تبديل کند.

وقفه های خارجی سخت افزاری

وقفه های خارجی سخت افزاری (external hardware-interrupts) خارج از CPU و توسط دستگاه های جانبی ، مانند صفحه کليد، چاپگر، کارت های ارتباطی و يا کمک پردازنده توليد می شوند.

دستگاه های جانبی با ارسال وقفه به CPU خواستار قطع اجرای برنامه فعلی شده و CPU را متوجه خود می کنند. آنها به پايه (maskable interrupts) INTR يا (non maskable interrupts) NMI پردازنده متصل هستند.

وقفه های دستگاه ها می توانند از طريق مداری به نام PIC 8259A، که کارش منحصرا سروکار داشتن با اين نوع وقفه هاست، به پردازنده ارسال شوند. مدار (programmable interrupt controller) PIC که توسط CPU کنترل می شود سيگنال هايش را روی پايه INTR قرار می دهد و امکان فعال و غيرفعال کردن وقفه ها و تغيير سطح الويت را تحت نظارت يک برنامه می دهد.

دستورات STI و CLI می توانند برای فعال و غيرفعال کردن وقفه هایی که روی پايه INTR ارسال می شوند بکار روند که البته روی وقفه های NMI تاثيری ندارد.

وقفه های نرم افزاری

وقفه های نرم افزاری (software interruptions) در نتيجه دستورالعمل int در يک برنامه درحال اجرا توليد می شوند.

برنامه نويس می تواند با دادن دستور int يک وقفه نرم افزاری توليد کند. بدين طريق بلافاصله اجرای برنامه فعلی را متوقف می کند و CPU را به روتين وقفه هدايت می کند. برنامه نويس از طريق وقفه ها می تواند در برنامه با وسايل جانبی ارتباط برقرار کند. استفاده از وقفه ها باعث کوتاهتر شدن کد برنامه و درک آسانتر و اجرای بهترآن می شود.

روتين های وقفه نرم افزاری بخشی از سيستم عامل هستند. از اينرو وقفه های نرم افزاری را می توان به دو گروه تقسيم کرد؛ وقفه های سيستم عامل DOS و وقفه های BIOS. وقفه های DOS آسانتر استفاده می شوند اما از وقفه های BIOS که قسمتی از سخت افزار هستند کندتر هستند.

DOS اين نوع وقفه ها را برای اجرای (application programming interface) API خودش استفاده می کند. بيشتر سيستم عامل های جديد مانند Windows و Unix واسطه C-based را استفاده می کنند.


INT

دستورالعمل (interrupt) int يک روتين وقفه را فراخوانی می کند. فرم کلی آن به صورت زير است:

int n

n شماره وقفه موردنظر و مقداری بين 0 تا 255 است که اجازه فراخوانی 256 روتين مختلف وقفه را می دهد.

دستورالعمل int يک فراخوانی سيستمی را می سازد و شکل خاصی از دستورالعمل فراخوانی يک زيربرنامه (دستورالعمل call) است.

مشکل دستورالعمل int اين است که تنها 256 روتين وقفه را می تواند پشتيبانی کند. درحاليکه DOS به تنهايی دارای بيش از 100 سرويس مختلف وقفه و BIOS بيش از هزاران سرويس وقفه است. که اين تعداد بيش از کليه وقفه هايی است که توسط اينتل رزرو شده است. برای حل اين مشکل از يک شماره وقفه برای هر دسته از سرويس های وقفه و يک شماره تابع برای تعيين سرويس موردنظر استفاه می شود. شماره تابع توسط يکی از ثبات ها (اکثرا AH) هنگام فراخوانی وقفه ارسال به روتين وقفه می شود.


مثال. سيستم عامل DOS شماره وقفه 21h را بکار می گيرد. برای انتخاب يک تابع خاص، قبل از فراخوانی وقفه، کد تابع در ثبات AH قرار می گيرد. برای نمونه تابع 4Ch اين وقفه برای خاتمه برنامه و برگشت به محيط DOS فراخوانی می شود.

mov AH, 4Ch
int 21h


جدول بردار وقفه

هر سطح وقفه يک محل رزرو شده در حافظه دارد که بردار وقفه (interrupt vector) ناميده می شود. همه بردارهای وقفه در جدولی به نام جدول بردار وقفه (interrupt vector table) نگهداری می شوند. اين جدول از ابتدای حافظه اصلی يعنی آدرس 0000:0000 ذخيره شده است.

هر بردار وقفه 4 بايت طول دارد. دوبايت بالای آن آفست و دو بايت پايين آن سگمنت روتين وقفه را دربر می گيرند. چون 256 روتين های وقفه وجود دارد بنابراين اندازه جدول بردار وقفه 256×4=1024=1KB است.

شماره وقفه به عنوان انديسی برای جدول بردار وقفه استفاده می شود. آفست روتين وقفه شماره n در آدرس n×4 و آدرس سگمنت روتين وقفه شماره n در آدرس n×4+2 جدول قرار دارد.

يک ويژگی خوب اين سيستم اين است که می توان بردارها را برای اشاره به روتين ديگری تغيير داد. که اين همان کاری است که برنامه های TSR (Terminate and Stay Resident) انجام می دهند.

در برنامه هميشه توسط شماره وقفه به يک روتين وقفه مراجعه می شود بنابراين برنامه نيازی به دانستن آدرس واقعی در حافظه ندارد و آدرس روتين وقفه هنگام اجرا توسط CPU تعيين می شود.


مثال. آدرس های آفست و سگمنت روتين وقفه شماره 5 برابر با 5×4=0014h و 5×4+2=0016h می باشد.


چند نمونه وقفه متعارف

وقفه 21h

تابع 01h. يک کليد را از صفحه کليد می خواند.
کد کليد خوانده شده در ثبات AL برگردانده می شود.

mov AH, 0lh
int 21h
mov AL, character

تابع 02h. يک کاراکتر را روی صفحه نمايش نشان می دهد.
کد کاراکتر در ثبات DL بايد قرار داده شود.

mov AH, 02h
mov DL,character
int 21h

تابع 09h. يک رشته کاراکتری را روی صفحه نمايش نشان می دهد.
آدرس شروع رشته بايد در ثبات های DS:DX قرار بگيرد. انتهای رشته توسط کاراکتر ($) بايد تعيين شده باشد.

mov AH,09h
lea DX, string
int 21h

وقفه 10h

تابع 02h. مکان نما را روی صفحه نمايش به سطر و ستون خاصی منتقل می کند.

شماره صفحه در BH، شماره سطر در DH و شماره ستون در DL بايد قرار بگيرد. مختصات صفحه از نقطه 0 و 0 از گوشه بالای چپ صفحه نمايش شروع می شود.

mov AH, 02h
mov BH, page
mov DH, row
mov DL, column
int 10h

تابع 09h. يک کاراکتر را با رنگ معين چندبار نمايش می دهد.
کد کاراکتر در AL، شماره صفحه در BH، خاصيت رنگ کاراکتر در BL و تعداد تکرار کاراکتر در CX بايد قرار بگيرد.

mov AH, 09h
mov AL, character
mov BH, page
mov BL, attribute
mov CX, number
int 10h

زير برنامه (procedure) مجموعه ای از دستورات است که يکبار تعريف و به دفعات استفاده می شود. با بکارگيری زيربرنامه خوانائی برنامه بالاتر رفته و از تکرار دستورات مشابه جلوگيری می شود. علاوه براين اشکال زدائی و تغيير برنامه آسان تر انجام گيرد.

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


تعريف زيربرنامه

تعريف زيربرنامه بايد در سگمنت کد انجام بگيرد. از دو راهنمای proc و endp برای تعيين بلاک زيربرنامه استفاده می شود.

ProcedureName PROC [NEAR|FAR]
     ...
     RET
ProcedureName ENDP

Procedurename نام زيربرنامه است که قبل از راهنماهای proc و endp قرار می گيرد و بايد يکسان باشد. عملوند near يا far اختياری است. کلمه near به اسمبلر می گويد که زيربرنامه از نوع داخلی است. برای تعريف يک زيربرنامه خارجی از کلمه far به جای near استفاده می شود.

دستور ret باعث خروج از زيربرنامه و برگشت به فراخواننده می شود.


نکته. اگر عملوندی مقابل تعريف زيربرنامه قرار نگيرد از نوع near در نظر گرفته می شود.
نکته. اگرچه تعريف يک زيربرنامه که عملا داخلی است به صورت خارجی اشکالی ايجاد نمی کند ولی بهتر است اين کار را نکنيد.


مثال. زيربرنامه جمع دو عدد در AH و AL و نگهداری مجموع در ثبات BX.

Adding PROC near
     mov BX, AL
     add BX, AH
     ret
Adding ENDP

مثال: زيربرنامه Putc برای نمايش کاراکتری که در ثبات al قرار دارد.

Putc PROC
     mov DL,AL
     mov AH,02
     int 21h
     ret
Putc ENDP


زيربرنامه های near و far

دو نوع زيربرنامه وجود دارد داخلی (intrasegment) و خارجی (intersegment).

• زيربرنامه های داخلی در همان سگمنتی که تعريف شده اند قابل فراخوانی هستند و در تعريف آنها از صفت near استفاده می شود.
• زيربرنامه های خارجی روال هائی که در سگمنت ديگری قرار دارند و از ساير سگمنت ها قابل فراخوانی می باشند و در تعريف آنها از صفت far استفاده می شود. زيربرنامه های خارجی درفايل جداگانه ای قرار دارد و هنگام لينک کردن بايد به برنامه پيوند داده شوند. نتيجه کار بعد از لينک مانند زيربرنامه داخلی است.

فراخوانی از نوع near کنترل را درون همان سگمنت کد جابجا می کند وتنها مقدار IP در پشته ذخيره می شود. فراخوانی far کنترل را بين سگمنت های مختلف عبور می دهد. هر دو مقادير CS و IP در پشته قرار می گيرند.

نکته. دستورات call و ret نوع فراخوانی را مشخص نمی کنند بلکه عملوند near|far راهنمای proc به اسمبلر می گويد فراخوانی از کدام نوع است.


دستورات فراخوانی و بازگشت زيربرنامه

دودستورالعمل که پشته را استفاده می کنند و فراخوانی و برگشت زيربرنامه را انجام می دهند call و ret هستند. برای هدايت کنترل اجرا به زيربرنامه بايد آنرا فراخوانی کرد. زيربرنامه ها در هر کجای برنامه که به آن نياز داريم با دستور call فراخوانی می شوند. دستور call به صورت زير است:

call ProcedureName

دستورالعمل call باعث يک پرش غير شرطی به زيربرنامه می شود و آدرس دستورالعمل بعدی را در پشته ذخيره می کند. CPU در برخورد با دستور call به آدرس شروع زيربرنامه رجوع می کند و دستورات آنرا اجرا می نمايد. با برخورد به دستور ret به برنامه فراخوان بر می گردد و دستورات بعد از call را اجرا می نمايد.


مثال. فراخوانی زيربرنامه Putc.

call Putc

CPU در برخورد با دستور Call عمليات زير را انجام می دهد:

فراخوانی از نوع داخلی

1. مقدار ثبات IP (که حاوی آدرس دستور بعد از call است ) را در پشته ذخيره می کند.
2. آدرس ذکر شده مقابل دستور call را در ثبات IP قرار می دهد.

فراخوانی از نوع خارجی

1. مقدار ثبات CS را در پشته ذخيره می کند.
2. بخش سگمنت آدرس ذکر شده مقابل دستور call را در ثبات CS قرار می دهد.
3. مقدار ثبات IP را در پشته ذخيره می کند.
4. بخش آفست آدرس ذکر شده در جلوی دستور call را در ثبات IP قرار می دهد.

دستورالعمل ret آدرس ذخيره شده IP را از پشته بر می دارد و به برنامه اصلی بر می گردد. CPU در برخورد با دستور Ret عمليات زير را انجام می دهد:

بازگشت از زيربرنامه داخلی

1. مقدار ذخيره شده در پشته را در داخل ثبات IP قرار می دهد.

بازگشت از زيربرنامه خارجی

1. مقدار ذخيره شده در پشته را در داخل ثبات IP قرار می دهد.
2. مقدار ذخيره شده در پشته را در داخل ثبات CS قرار می دهد.

نکته. اگر دستور ret در انتهای زيربرنامه حذف شود کنترل اجرای برنامه به زيربرنامه بعدی می رود نه دستورالعمل بعدی در برنامه اصلی.
نکته. معمولا در ابتدای هر زيربرنامه بهتر است مقادير ثبات هائی که تغيير می کنند را در پشته ذخيره نمائيم و در انتهای زيربرنامه و قبل از دستور ret مقادير آنها را از پشته بازيابی کنيم. بايد توجه کنيم که دستورات pop متناظر با دستورات push باشند و کليه داده هائی که در زيربرنامه در پشته push شده اند بايد pop شوند وگرنه به با دستور ret به آدرس درست پرش نمی کند.


مثال. زيربرنامه برای نمايش 40 کاراکتر space. توجه کنيد زيربرنامه Putc درون زيربرنامه PrintSpaces فراخوانی شده است.

PrintSpaces PROC near
                push AX
                push CX
                mov AL, ' '
                mov cx, 40
PSLoop:   call putc
                loop PSLoop
                pop CX
                pop AX
                ret
PrintSpaces ENDP

در ابتدای زيربرنامه ثبات های AX و CX در پشته قرار می گيرند و در انتها به ترتيب عکس بازيابی می شوند. زيربرنامه فوق به صورت زير فراخوانی می شود.

call PrintSpaces


ارسال و دريافت پارمترها

پارامترها مقاديری هستند که می توانيد به زيربرنامه بدهيد يا بگيريد. برای ارسال يا دريافت پارامترها معمولا از ثبات، متغيرهای سراسری يا پشته استفاده می شود.

ارسال پارامتر از طريق ثبات

مثال. زيربرنامه زير طول يک رشته را محاسبه و در ثبات CX برمیگرداند. آدرس شروع رشته در ثبات SI قرار دارد.

StrLen PROC
           push SI
           mov CX,0
Whl:   cmp Byte Ptr[SI],'$'
           jc EndW
           inc CX
           inc SI
           jmp Whl
EndW: pop SI
           ret
StrLen ENDP

ارسال پارامتر از طريق پشته

پارامترهائی که به زيربرنامه داده می شوند را می توان قبل از فراخوانی زيربرنامه در پشته اضافه کرد. پارامترها در زيربرنامه pop نمی شوند بلکه مستقيما از پشته دسترسی می شوند زيرا قبل از دستور call در پشته اضافه شده اند و آدرس برگشتی بعد از آن اضافه می شود. علاوه براين چون ممکن است در چندين جای زيربرنامه استفاده شوند معمولا درون ثبات نگهداری نمی شوند و بهتر است در حافظه پشته باقی بمانند.

يک برنامه خارجی که يک پارامتر از طريق پشته را ارسال می کند در نظربگيريد. وقتی زيربرنامه درخواست می شود پارامتر می تواند با آدرس دهی غيرمستقيم [SP+4] دسترسی شود. اگر پشته هم در زيربرنامه برای ذخيره داده استفاده شود عدد بيشتری بايد به SP اضافه شود. ثبات BP را برای ارجاع به داده های درون پشته می توان به کار برد. ثبات SP با هر push و pop تغيير می کند اما BP ابتدا برابر با SP می شود و سپس ثابت می ماند در انتهای زيربرنامه مقدار اوليه BP بايد برگردانده شود. بعد از اينکه زيربرنامه تمام شد پارامترهائی که در پشته اضافه شده اند بايد حذف شوند.


مثال. تابع زير طول رشته را محاسبه و آدرس شروع رشته از طريق پشته به زيربرنامه ارسال می شود.

StrLen PROC
           push BP
           mov BP,SP
           mov SI,[BP+4]
           sub CX,0
Whl:   cmp byte ptr [SI],'$'
           jc Endw
           inc CX
           inc SI
           jmp Whl
EndW: pop BP
           ret
StrLen ENDP

مثال. محاسبه مجموع سه عدد که از طريق پشته به زيربرنامه ارسال شده اند.

ثابت ها

ثابت مشابه متغير محلی برای ذخيره داده ای است که توسط برنامه استفاده می شود. اما برخلاف متغير، مقدار ذخيره شده در يک ثابت در طی اجرای برنامه قابل تغيير نيست.

++C دو نوع ثابت واقعی و سمبليک دارد.

ثابت های واقعی

ثابت واقعی (literal constant) مقداری است که مستقيما در کد برنامه تايپ می شود.


مثال. مقادير 20 و 0.28 در عبارات زير ثابت های واقعی هستند که در متغيرهای count و tax_rate ذخيره می شوند.

int count = 20;
float tax_rate = 0.28;


مقادير ثابت برای نوع های پيش ساخته می تواند به صورت های دسيمال، اکتال، هگزادسيمال، مميزشناور يا کاراکتر باشند.

نقطه اعشار نشان دهنده ثابت مميزشناور است. ثابت های مميزشناور را می توان به صورت نماد علمی هم بيان کرد.


مثال. اعداد زير همگی ثابت های مميزشناورهستند.

123.456
0.019
100.
1.23E2 or 123
4.08e6 or 4080000
0.85e-4 or 0.000085


حروف f يا F برای ثابت های float و l يا L برای ثابت های long double را می توان به عنوان پسوند اضافه کرد در غير اينصورت با ثابت مميزشناور بعنوان يک عدد double برخورد می شود.

ثابتی که نقطه اعشار ندارد بعنوان ثابت صحيح تفسير می شود. ثابت های صحيح را به 3 صورت می توان نشان داد:

• ثابت دهدهی. اگر ثابت با هر عدد غير صفری شروع شود بعنوان يک عدد صحيح مبنای 10 تفسير می شود.. ثابت های دهدهی شامل ارقام 0 تا 9 و علامت + يا – می توانند باشند. اگر علامت نوشته نشود ثابت مثبت درنظر گرفته می شود.
• ثابت اکتال. اگر ثابت با رقم 0 شروع شود بعنوان يک عدد صحيح مبنای 8 تفسير می شود. ثابت های اکتال می توانند شامل ارقام 0 تا 9 و علامت + يا – باشند.
• ثابت هگزادسيمال. اگر ثابت با 0x يا 0X شروع شود بعنوان يک ثابت مبنای 16 با آن برخورد می شود. ثابت های هگزادسيمال می توانند شامل ارقام 0 تا 9 و حروف A تا F و علامت + يا – باشند.

ثابت های کاراکتری بين علامت کوتيشن (') قرارمی گيرند، مانند کاراکترهای 'A' و '0'. کاراکترهای خاص با علامت () نشان داده می شوند مانند 'n' (newline)،'t' (tab)،'' (backslash)،'r' (carriage return)،''' (single quote)،'"' (double quotes)، و غيره.

ثابت های سمبليک

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


مثال. برای محاسبه مساحت و محيط دايره در يک برنامه به جای نوشتن عدد 3.14 می توان ثابت PI را تعريف و استفاده کرد.

circumference = PI * (2 * radius);
area = PI * (radius)*(radius);

در اين حالت هم نوشتن برنامه راحت تر است و برنامه دارای خوانائی بيشتر است هم اگر نياز به تغيير ثابت پی به مقدار 3.14159 برای بالا بردن دقت محاسبات باشد اصلاح تنها در يک نقطه برنامه که ثابت تعريف شده است صورت می گيرد نه کل برنامه.


تعريف ثابت سمبليک

دوروش برای تعريف ثابت های سمبليک وجود دارد: راهنمای define# و کلمه کليدی const.

راهنمای define# در قسمت پيش پردازنده ها بيشتر توضيح داده خواهد شد. فرم کلی آن به صورت زير است:

#define CONSTNAME literal

CONSTNAME نام ثابت و literal مقدار واقعی آن است. راهنمای define# به کامپايلر دستور می دهد که درسرتاسر کد برنامه CONSTNAME را با literal جايگزين کند.

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


مثال. ثابت PI با مقدار 3.14159 تعريف شده است.

#define PI 3.14159


دقت کنيد که خط define# به سميکولن(;) ختم نمی شود. define# می تواند در هر کجای برنامه باشد ولی معمولا همگی در قسمتی از ابتدای کد برنامه و قبل از تابع main() هستند.

روش دوم تعريف يک ثابت سمبليک استفاده از کلمه کليدی const است. const را می توان به اول هر اعلان متغيری اضافه کرد. در اين صورت متغير در طول اجرای برنامه قابل تغيير نخواهد بود. اگر برنامه سعی به تغيير آن کند خطای کامپايلر صادر خواهد شد.


مثال.

const int count = 100;
const float pi = 3.14159;
const long debt = 12000000, float tax_rate = 0.21;


const روی کليه متغيرهای خط اعلان تاثير می گذارد.

تفاوت ثابت هائی که با #define و const تعريف می شوند در حوزه آنهاست. وقتی از #define استفاده می کنيد کنترل ثابت ها را از حوزه کامپايلر خارج می کنيد؛ type checking روی اسم آن انجام نمی گيرد و آدرس آنرا قابل بازيابی نيست و اشاره گريا ارجاعی به آن ممکن نيست و نمی تواند از نوع user-defined باشد. اما اگر ثابت توسط const تعريف شده باشد می تواند از هر نوع داده استاندارد يا user-defined باشد. آدرس آن هم قابل بازيابی است و مانند يک متغير دارای حوزه دسترسی است بنابراين ثابتی که درون يک تابع تعريف می شود در ساير نقاط برنامه شناخته شده نيست.

مقداردهی اوليه متغيرهای عددی

هنگام اعلان يک متغير، با وجوديکه مقدار آن هنوز تعيين نشده است، به کامپايلر فرمان داده می شود تا فضای لازم برای متغير را کنار بگذارد. در اين حالت مقدار متغير می تواند صفر يا يک مقدار تصادفی باشد. قبل از استفاده از متغير هميشه بايد آن را با يک مقدار مشخص مقداردهی کرد. اين کار موقع اعلان متغير می تواند صورت بگيرد. برای اينکار بعد از اسم متغير علامت مساوی و مقدار اوليه موردنظر را ذکر کنيد.


مثال.

int count = 0;
double percent = 0.01, taxrate = 28.5;


علامت مساوی (=) عملگر واگذاری در زبان C است که در بخش عبارات توضيح داده می شود.

توجه کنيد مقداراوليه متغير خارج از محدوده مجاز نباشد. کامپايلر چنين خطائی را گير نمی اندازد و برنامه ممکن ا ست هنگام اجرا نتايج غيرمنتظره ای توليد کند.


نکته. با تعداد بايت هائی که نوع های متغير روی کامپيوتر شما اشغال می کند به خوبی آشنا شويد.
نکته. از typedef برای خوانا کردن برنامه خود استفاده کنيد.
نکته. تاحد ممکن هنگام تعريف متغير به آنها مقداراوليه بدهيد. استفاده از متغيری که مقداردهی نشده است ممکن است نتايج غيرقابل پيش بينی توليد کند.
نکته. استفاده از متغيرهای float و double برای ذخيره اعداد صحيح باعث پايين آمدن کارائی برنامه می شود.
نکته. مقادير بزرگ را در نوع متغيری که برای ذخيره آنها کوچک است ذخيره نکنيد.
نکته. اعداد منفی را در نوع های بدون علامت ذخيره نکنيد.

 

در زبان برنامه نويسی C هر متغير قبل از استفاده بايد اعلان شود. اعلان متغير کامپايلر را از نام، نوع و مقدار اوليه متغير آگاه می کند. اگر برنامه سعی کند از متغيری استفاده کند که قبلا اعلان نشده است کامپايلر پيغام خطا صادر می کند.

اعلام متغير به فرم کلی زير است:

typename varname;

typename نوع متغير را مشخص می کند که بايد يکی از نوع های داده ای زبان C باشد. varname نام متغير است که بايد از قواعد گفته شده تبعيت کند.

می توان در يک خط چند متغير را از يک نوع تعريف کرد.


مثال. متغيرهای count، number و start از نوع int و متغيرهای percent و total از نوع float اعلان شده اند.

int count, number, start;   /* three integer variables */
float percent, total;          /* two float variables */


در بخش توابع درقسمت حوزه متغيرها درباره محل اعلان متغير در برنامه توضيح داده شده است. فعلا کليه متغيرها را در آغاز تابع ()main اعلان کنيد.


کلمه کليدی typedef

کلمه کليدی typedef برای ايجاد نامی جديد به نوع داده موجود بکار می رود و در واقع يک مترادف برای آن نوع توليد می کند.


مثال. عبارت زير برای نوع داده ای int مترادف integer را ايجاد می کند. بنابراين در برنامه می توان از کلمه integer برای اعلان متغيرهای از نوع int استفاده کرد.

typedef int integer;
integer count;


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

انواع داده عددی

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

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

انواع متغير عددی در دو دسته کلی قرار می گيرند:

• متغيرهای صحيح، مقاديری را نگه می دارند که بخش کسری ندارند. متغيرهای صحيح خود دو نوع هستند: علامتدار، که می توانند مقادير مثبت و منفی را ذخيره کنند و بدون علامت، که تنها مقادير مثبت را نگه می دارند.
• متغيرهای مميزشناور، مقاديری را که دارای بخش کسری هستند يعنی اعداد حقيقی را نگه می دارند.


عبارات signed، unsigned، short و long اصلاح کننده هائی هستند که برای تغيير و تبديل انواع پايه از قبيل char، int و double اضافه می شوند .

انواع داده ها وابسته به platform کامپيوتر است و ممکن است روی کامپيوترهای مختلف متفاوت باشد، اما C با توجه به استاندارد ANSI موارد زير را تضمين می دهد:

• يک کاراکتر هميشه يک بايت است.
• اندازه short کوچکتر يا مساوی اندازه int است.
• اندازه int کوچکتر يا مساوی اندازه long است.
• اندازه unsigned برابر با int است.
• اندازه float کوچکتر مساوی با اندازه double است.

 

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

نام متغير

هر متغير دارای يک نام است. در زبان C اسامی متغير ها بايد از قوانين زير پيروی کند:

• اسم می تواند شامل حروف، ارقام و کاراکتر زيرخط ( _ ) باشد.
• اولين حرف اسم متغير بايد يک حرف باشد. زير خط هم می تواند در ابتدای اسم متغير بکار برود ولی توصيه نمی شود.
• بزرگ و کوچک بودن حروف مهم است، بنابراين اسامی count و Count به دو متغير جداگانه اشاره دارند. برنامه نويسان اغلب از حروف کوچک برای متغير ها استفاده می کنند و اسامی با حروف بزرگ معمولا برا ثابت ها بکار می رود.
• کلمات کليدی نمی توانند به عنوان نام متغير استفاده شود.


مثال. چند نمونه از اسامی مجاز و غير مجاز در جدول زير ديده می شود:

مجازبودن نام متغير
مجاز Percent
مجاز y2x5__fg7h
مجاز annual_profit
مجاز، ولی توصيه نمی شود _1990_tax
غير مجاز، کاراکتر# savings#account
غيرمجاز، کلمه کليدی double
غيرمجاز، اولين کاراکتر رقمی 9winter

در بعضی کامپايلرها نام متغير می تواند 31 کاراکتر (در ++C استاندارد 1024 کاراکتر) طول داشته باشد؛ يعنی کامپايلر تنها 31 کاراکتر اول نام را درنظر می گيرد. با اين طول می توان نامی برای متغير انتخاب کرد که معنی داده ذخيره شده در آن را منعکس کند.

نام متغير کمک به روشن شدن کاربرد آن برای کسی که source برنامه را نگاه می کند .


مثال. در برنامه ای که پرداخت های وام را محاسبه می کند مقدار بهره را می توان در متغير interest_rate ذخيره کرد.


مرسوم است از زيرخط برای جدا کردن متغيرهای چند کلمه ای استفاده شود. يا ازروش نام گذاری کوهانی (camel notation) که حرف اول هر کلمه بزرگ است پيروی می شود.


مثال. متغيری که بهره بانکی را ذخيره می کنذد می تواند به دو صورت interest_rate يا InterestRate تعريف شود.


نکته. نامهای توصيفی برای متغيرها انتخاب کنيد.
نکته. به سبکی که برای نامگذاری متغير ها انتخاب کرده ايد در کل برنامه وفادار بمانيد.
نکته. شروع نام متغير با زيرخط غير ضروری است.
نکته. نامگذاری متغير همگی با حروف بزرگ غير ضروری است.

در اين صفحه دستورات حلقه و نحوه پياده سازی ساختارهای حلقه های تکرار توضيح داده می شود.

LOOP
LOOPE/LOOPZ
حلقه های تکرار ديگر


LOOP

در زبان اسمبلی از دستور loop برای ساختن حلقه های شمارشی کاهشی با بدنه کوچک استفاده می شود. فرم کلی آن به صورت زير است:

loop target

دستورالعمل loop ثبات CX را يک واحد کم می کند سپس اگر مقدار جديد CX مخالف با صفر باشد به آدرس target پرش می کند. اگر CX برابر با صفر باشد دستور بعدی اجرا می شود.

ثبات CX به عنوان شمارنده عمل می کند و تعداد تکرار حلقه بايد ابتدا در ثبات CX قرار بگيرد.


مثال. دستورات زير مجموع اعداد 1 تا 10 را محاسبه و در ثبات AX ذخيره می کند.

      mov AX, 0
      mov CX, 10
lbl:
      add AX, CX
      loop lbl


توجه کنيد چون اين دستور ابتدا از CX يک واحد کم می کند، اگر CX قبلا حاوی صفر باشد بعد از کاهش برابر با مقدار 65535 می شود بنابراين حلقه 65536 بار تکرار خواهد شد.

دستورالعمل loop مشابه دستورات پرش کوتاه محدوده به 128 بايت است و برای حلقه با بدنه کوچک مناسب است. برای حلقه های تکرار با بدنه بيشتر می توانيد از دستورات پرش برای ساختن حلقه تکرار استفاده نمائيد.

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

دستورالعمل loop روی هيچکدام از ثبات ها تاثير ندارد.


LOOPE/LOOPZ

دستورالعمل های loopz و loope مشابه دستور loop می باشند با اين تفاوت که پرش در صورتی انجام می گيرد که CX مخالف با صفر و فلگ Z مساوی با يک باشد.

اين دستورات برای استفاده بعد از دستور cmp مفيد است.


مثال. دستورات زير اولين عنصر غيرصفر را در آ رايه 15 تائی Array جستجو می کند. اگر کليه عناصر آرايه صفر باشد بعد از اجرای حلقه به آدرس AllZero پرش می کند.

      lea SI, Array
      dec SI
      mov cx, 15
Search:
      inc SI
      cmp byte ptr [SI], 0
      loope Search
      je AllZero


حلقه های تکرار ديگر

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

مثال. دستورات زير مجموع اعداد 1 تا 10 را محاسبه و در ثبات AX ذخيره می کند.

       mov AX, 0
       mov CX, 1
For:
      cmp CX, 10
      jle Repeat
      jmp EndFor
Repeat:
      add AX, CX
      inc CX
      jmp For
EndFor:

مثال. دستورات زير کاراکترهائی را از کاربر گرفته و در يک آرايه ذخيره می کند تا وقتی که کليد enter وارد شود.

      lea SI, Array
Readkey:
      mov AH, 1
      int 21h           ;Get a character
      cmp AL, 13     ;Carriage return ASCII code
      je EndLoop
      mov [SI],AL    ;Save input character in Array
      inc SI
      jmp Readkey
EndLoop:

تعداد صفحات : 425

اطلاعات کاربری
آمار سایت
  • کل مطالب : 4247
  • کل نظرات : 0
  • افراد آنلاین : 4
  • تعداد اعضا : 2926
  • آی پی امروز : 67
  • آی پی دیروز : 161
  • بازدید امروز : 467
  • باردید دیروز : 830
  • گوگل امروز : 6
  • گوگل دیروز : 51
  • بازدید هفته : 467
  • بازدید ماه : 35,408
  • بازدید سال : 110,517
  • بازدید کلی : 8,289,211
  • کدهای اختصاصی