بایگانی دسته: آموزش برنامه‌نویسی

گزارش اختصاصی از مسابقه‌ی برنامه‌نویسی بیان (ویرایش: عکس‌ها اضافه‌شدند)

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

بنر کانتست بیان
بنر کانتست بیان

از آنجا که بنده هم فرصت شرکت در این مسابقه‌ی برنامه‌نویسی (کانتست) را داشتم، تصمیم گرفتیم که در اینجا گزارشی از نحوه برگزاری و رویدادهای شنبه را بنویسم.

شرکت خصوصی بیان سال گذشته کانتستی را برگزار کرد، که در دو قسمت دانش‌آموزی و آزاد برگزار می‌شد. شرکت در قسمت آزاد محدودیتی نداشت، ولی بخش دانش‌آموزی (همان‌گونه که از اسم آن برمی‌آید!) ویژه‌ی دانش‌آموزان بود. این کانتست سه مرحله داشت که دو مرحله‌ی نخست آن به شکل آنلاین برگزار شدند و برگزیدگان مرحله‌ی دوم به مرحله‌ی حضوری راه یافتند، که در شرکت بیان برگزار شد. من درباره‌ی روند برگزاری نخستین کانتست بیان اطلاع چندانی ندارم؛ بنابراین از ذکر جزئیات بیشتر خودداری می‌کنم.

امسال نیز دومین کانتست بیان طبق برنامه برگزار شد. وجه تمایز این کانتست، که سبب بازتاب گسترده‌ی داخلی آن شد، بین‌المللی بودن آن است. امسال شرکت بیان با همکاری سایت Codeforces مرحله‌ی گزینش این کانتست را به زبان انگلیسی و برای شرکت‌کنندگان خارجی نیز برگزار کرد. سایت Codeforces یکی از معتبرترین و مشهورترین سایت‌های برگزارکننده‌ی کانتست‌های آنلاین است، که پیش از این هم مسابقاتی مانند VKCup را برگزارکرده‌است.

روند گزینش
روند گزینش شرکت‌کنندگان مرحله‌ی حضوری

نتیجه این که برخی از برترین برنامه‌نویسان جهان در زمینه کانتست برای شرکت در مرحله‌ی حضوری برگزیده‌شدند. برخی از آن‌ها عبارتند از:

  • گنادی کوروتکویچ (tourist) از بلاروس، دارنده‌ی 6 مدال طلای المپیاد جهانی کامپیوتر که دوتای آن‌ها را با حدّاکثر نمره‌ی ممکن کسب کرده است. همچنین نفر اوّل جهان در سایت Codeforces
  • میخاییل کِوِر (cerealguy)، نفر 24ام جهان در سایت Codeforces (مطمئن نیستم، ولی احتمالاً در ACM هم مقام آورده‌است)
  • ماکوتو سوجیما (rng_58) از ژاپن، نفر دوم جهان در سایت Codeforces
  • پیتر شیه (peter50216) از تایوان، نفر ششم جهان در سایت Codeforces
  • ایگور کولیکو (Egor) از روسیه، نفر پنجم جهان در سایت Codeforces

همچنین برنامه‌نویسان دیگری از چین، لهستان، ایالات متّحده و اوکراین نیز برگزیده‌شدند که در نهایت، برخی از آن‌ها در مرحله‌ی حضوری شرکت‌کردند.

فهرست شرکت‌کنندگان کانتست بین‌المللی و رتبه‌هایشان را در اینجا و فهرست شرکت‌کنندگان ایرانی و رتبه‌های آن‌ها را در اینجا می‌توانید ببینید.

پس از برگزاری مراحل آنلاین و گزینش شرکت‌کنندگان مرحله‌ی حضوری، اعلام شد که مرحله‌ی حضوری در تاریخ 27 بهمن و در دانشگاه شریف برگزار خواهد شد، که در نهایت تاریخ به شنبه 28ام تغییر یافت و مکان نیز به هتل آزادی پارسیان تهران منتقل شد.

امّا پس از این مقدمه‌ی طولانی، به اصل ماجرا و مرحله‌ی بین‌المللی مسابقه می‌رسیم.

شنبه صبح که وارد هتل شدم، علاوه بر شماری از شرکت‌کنندگان ایرانی، شرکت‌کنندگان خارجی نیز در لابی مستقر بودند. متأسّفانه تصویر مناسبی از شرکت‌کنندگان خارجی در لابی پیدا نکردم، امّا ایوان رومانوف تصاویر خوب (و زیادی!) تهیه کرده که می‌توانید آن‌ها را در بلاگ او در Codeforces ببینید. بر اساس آنچه که رومانوف در بلاگش نوشته، شرکت‌کنندگان خارجی از پنجشنبه تا یکشنبه در ایران بوده‌اند.

چند نفر از شرکت کنندگان ایرانی در لابی هتل - Codeforces.com
چند نفر از شرکت کنندگان ایرانی در لابی هتل – Codeforces.com

افرادی که در عکس بالا دیده می‌شوند (از راست به چپ):

فرزاد عبدالحسینی (مدال طلای کشوری المپیاد کامپیوتر) – سیّد حامد ولی‌زاده (مدال طلای جهانی المپیاد کامپیوتر و نفر سوم مسابقه بیان در ایران) – نمی‌شناسم – حامد صالح (مدال طلای کشوری المپیاد کامپیوتر) – علیزضا فرهادی (مدال نقره‌ی جهانی المپیاد کامپیوتر) – نمی‌شناسم

لابی هتل از بالا - Codeforces.com
یلابی هتل از بالا – Codeforces.com

در سمت راست تصویر، شرکت‌کنندگان خارجی قرار دارند. (آن‌هایی که تی‌شرت زرد پوشیده‌اند)

در میان ایرانی‌ها، همه‌ی اعضای تیم المپیاد جهانی کامپیوتر ایران (که امسال در ایتالیا برگزار شد) حضور داشتند (سعید ایلچی و حامد ولیزاده که مدال طلا گرفتند و علیرضا فرهادی و محمدرضا ملکی که نقره شدند). علاوه بر آن، بسیاری از شرکت‌کنندگان دیگر نیز مدال‌آوران کشوری و جهانی امسال و سال‌های گذشته بودند. در میان شرکت‌کنندگان خارجی نیز افراد زیر حضور داشتند (البته برخی از آن‌ها در لابی هتل شناسایی نشدند!):

Egor, cerealguy, peter50216, liympanda, watashi, kelvin, Dmitry_Egorovanrieff, ivanromanov

ویرایش: از آنجا که در کانتست گزینشی بیان، نام ایوان رومانوف در بیست نفر برتر دیده نمی‌شود، احتمال می‌رود که او تنها برای تهیه‌ی گزارش به ایران آمده‌باشد.

ایوان رومانوف در تمام این مدت وقایع را به شکل زنده پوشش می‌داد که حاصل آن را می‌توانید در بلاگ او در Codeforces ببینید. نکته فرعی جالب هم این که، علی‌رغم اسمش، او از کشور سوییس به ایران آمده‌بود.

در این مسابقه، شرکت بیان رایانه‌ای را به شرکت‌کنندگان ارائه نمی‌داد و همه با لپتاپ شرکت می‌کردند. به همین دلیل، برای تنظیم سیستم‌ها نیز زمانی در نظر گرفته‌شده‌بود. بر اساس برنامه، مسابقه باید در ساعت 10 صبح آغاز می‌شد؛ اما با تأخیر روبه‌رو شد و (پس از تحویل تی‌شرت‌ها و تنظیم سیستم‌ها) ساعت 12:32 دقیقه آغاز شد.

Codeforces.com
Codeforces.com

در این مسابقه، 7 سوال برای 3 ساعت درنظرگرفته‌شده‌بودند که یک ربع پیش از پایان این زمان، کانتست به مدّت نیم‌ساعت تمدید شد و در نهایت سه‌ساعت و نیمه برگزار شد. سوال‌ها سخت بودند، به گونه‌ای که بسیاری از شرکت‌کنندگان 0 تا 1 سوال حل کردند! طبق آماری که بعداً اعلام شد، نفر نخست جهان 4 سوال و نفر نخست ایران 2 سوال حل کرده‌اند. سوالات مسابقه هنوز در سایت بیان قرار نگرفته‌اند، ولی احتمالاً به زودی در آنجا قرار خواهند گرفت.

غرق در کانتست! - Codeforces.com
غرق در کانتست! – Codeforces.com

یکی از حواشی مسابقه‌ی اصلی این بود که صورت سؤال‌ها تنها به زبان انگلیسی موجود بود و ترجمه‌ی فارسی ارائه نشد. با وجود این که این مسئله مشکل‌ساز نشد، ولی از مسابقه‌ای که یک شرکت ایرانی در ایران برگزار می‌کند، انتظار می‌رود که سؤالات به زبان فارسی هم موجود باشند.

ویرایش: حاشیه‌ی جالب دیگر این بود که به ازای هر مسئله‌ای که یک نفر حل می‌کرد، بادکنکی با رنگی خاص (ویژه‌ی آن مسئله) جایزه می‌گرفت. این رسم مربوط به مسابقات ACM است. نویسندگان 2برنامه‌نویس قبلاً این رسم را در H2PL (لیگ برنامه‌نویسی راهنمایی حلّی 2)، KPL (همان لیگ که بعداً نامش تغییر کرد) و حلّی‌نت (مسابقه‌ی برنامه‌نویسی دبیرستان علّامه‌حلّی که سال گذشته پس از تأخیری چندین ساله برگزار شد و امسال برگزار نمی‌شود) دیده‌اند.

پس از این مسابقه و صرف نهار، چالش Funkoders (با k!) قرار بود برگزارشود که ماهیت آن را هنوز اعلام نکرده‌بودند، ولی شایعاتی وجود داشت مبنی بر آن که قرار است در این مسابقه، ایرانیان هم بتوانند در برابر رقبای خارجی قد علم کنند. در اصل، این برنامه هم یک کانتست با شیوه‌ی قضاوتی مشابه کانتست اصلی بود، ولی با این تفاوت که 15 سوال آسان و 42 دقیقه وقت داشت. البته در برنامه‌ی اصلی قرار بوده که این کانتست 2 ساعت به طول بینجامد؛ ولی به دلیل تأخیر در آغاز برنامه‌ی اصلی، زمان آن کاهش یافت.

ویرایش: یکی از حواشی مسابقه‌ی Funkoders حضور دو بازیگر بود که نقش مجسمه را ایفا می‌کردند و البته هر چند دقیقه یک بار هم تغییر وضعیت می‌دادند.

مجسمه‌ها - Codeforces.com
مجسمه‌ها – Codeforces.com

این مجسمه‌ها واقعاً به خوبی از پس نقششان برآمدند؛ چراکه با وجود خنده‌ها و تلاش‌های مجدّانه‌ی بنده و دوستان، مرتکب هیچ اشتباهی نشدند!

مجسمه‌ها - nardebaan.ir
مجسمه‌ها – nardebaan.ir

 

پس از آن، نوبت به صرف چای و کیک و استراحت در لابی رسید. بعد هم مراسم اختتامیه آغاز شد.

در مراسم اختتامیه، پس از پخش چند قطعه موسیقی زنده و غیرزنده و سرود ملی و تلاوت سوره‌ی حمد و سخنرانی مدیرعامل شرکت بیان، نوبت به اعلام برندگان رسید:

  • پیتر شیه از تایوان نفر اوّل جهان شد و به او مدال طلا، سه سکّه‌ی تمام بهار آزادی و صنایع دستی ایرانی (یک کوزه که فکر می‌کنم میناکاری شده‌بود) تعلّق گرفت. 
  • میخاییل کِوِر نفر دوم جهان شد و مدال نقره، دو سکّه‌ی تمام بهار آزادی و صنایع دستی ایرانی برد.
  • بر خلاف انتظارات، ایگور کولیکو اوّل نشد و سوم شد و مدال برنز، یک سکّه‌ی تمام بهار آزادی و صنایع دستی ایرانی هدیه گرفت.
سه نفر اوّل جهان - nardebaan.ir
سه نفر اوّل جهان – nardebaan.ir

از راست به چپ: پیتر شیه، میخاییل کِوِر، ایگور کولیکو

 

علاوه بر آن، به نفرات برگزیده‌ی ایران نیز جوایزی اهدا شد:

  • سهیل احسانی نفر نخست ایران شد. به او مدال طلا و یک و نیم میلیون تومان وجه نقد تعلّق گرفت.
  • علی فیوج نوملی نفر دوم ایران شد و مدال نقره و یک میلیون تومان وجه نقد برد.
  • سید حامد ولی‌زاده نفر سوم ایران شد و مدال برنز و پانصدهزار تومان وجه نقد جایزه گرفت.
سه نفر برتر ایران - nardebaan.ir
سه نفر برتر ایران – nardebaan.ir

نتایج نهایی را در این نشانی می‌توانید ببینید. البته برخی شرکت‌کنندگان در این جدول حضور ندارند که احتمالاً هیچ سوالی حل نکرده‌اند. (من هم در این جدول حضور ندارم!) نکته جالب این که تمامی 5 نفر نخست ایران، 2 سوال حل کرده‌بودند! و تفاوت میان نفر سوم و چهارم ایران کمتر از یک نمره بود!

پس از مراسم اختتامیه نیز طبق برنامه ضیافت شام برگزار شد که واقعاً جای تقدیر داشت.

سخن پایانی

فکر می‌کنم که این مسابقه، نخستین تجربه‌ی این‌چنینی در ایران بوده‌باشد. کیفیت برگزاری مسابقه واقعاً عالی بود. با این وجود، سخت‌بودن بیش از حدّ سوال‌های کانتست اصلی، باعث نارضایتی برخی از شرکت‌کنندگان شد. با این وجود، چنین رویدادهایی واقعاً جای تقدیر و تشکّر دارند و برگزارشدن آن‌ها در ایران واقعاً مایه‌ی افتخار است. امیدوارم که هزینه‌ی سنگین و برخی مشکلات دیگر جلوی تکرار چنین رویدادهایی را نگیرد. به هر کسی که دستی در برنامه‌نویسی دارد، توصیه می‌کنم که مسابقه‌ی سال بعد بیان را از دست ندهد.

مسئله‌ای که بیش از همه جای تأمّل داشت، این بود که در میان پنج نفر برتر جهان، خبری از ایرانیان نبود که با توجه به شرایط، این یک باخت در خانه به حساب می‌آید. البته با توجه به این که شرکت‌کنندگان خارجی از میان برترین برنامه‌نویسان جهان انتخاب شده‌بودند، واقعاً این پدیده قابل پیش‌بینی بود؛ ولی باز هم باید تلاش کنیم و امیدوار باشیم که در مسابقه‌های بعدی، بدون درنظرگرفتن سهمیه برای ایرانیان، سه نفر از آن‌ها رتبه‌های برتر را تصاحب کنند.

منبع: در نوشتن این مطلب، علاوه بر مشاهدات شخصی، از تصاویر و مطالب وبلاگ رسمی شرکت بیان و وبلاگ و سایت کانتست بیان نیز استفاده کردم. علاوه بر آن، از برخی مطالب موچود در سایت Codeforces، به ویژه بلاگ ایوان رومانوف، نیز استفاده کردم. برای عکس‌ها، علاوه بر این منابع، از سایت نردبان نیز استفاده‌شده‌است.

شما از چنین کانتستی چه انتظاری دارید؟ آیا مسابقه‌ی امسال به نظر شما رضایت‌بخش بود؟

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

آموزش برنامه‌نویسی – بخش دوم – چند قدم جلوتر در راستای یادگیری مفاهیم!


سری جدیدی از آموزش‌های برنامه‌نویسی آغاز شده است. این سری منقضی شده است. پیشنهاد می‌کنیم این سری را ادامه ندهید!


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

شرط‌ها در پاسکال

در بیش‌تر مواقع ما نیاز به تصمیم‌گیری در مورد اطلاعات ورودی کاربر داریم. مثلا یک ماشین‌حساب ساده نیاز دارد بداند که در حال حاضر کدام عملگر را بین دو عدد ورودی اعمال کند. یعنی نیاز است که بررسی کنیم که کاربر کدام علامت (+ – / ×) را وارد کرده است؛ این کار با اعمال شروط امکان‌پذیر است.

ساختار کلی شرط‌ها

در پاسکال شرط‌ها به شکل زیر نوشته می‌شوند:

if {} then
	{Do something};

که پس از if باید شرط خود را قرار دهیم و پس از then نیز دستوری قرار می‌گیرد که اگر شرط درست بود باید اجرا شود.


کامنت‌ها

در بیش‌تر مواقع در برنامه‌نویسی شما نیاز خواهید داشت که توضیحاتی برای کدهای خود بنویسید. بزارید این‌طور توضیح دهم که فرض کنید شما برنامه‌ای با ۱۸۰۰۰ خط نوشته‌اید و در هنگام اجرا در خط ۱۵۴۳۶ام آن مشکلی پیش آمده است. مطمئنا انرژی خیلی‌خیلی‌خیلی زیادی باید صرف کنید تا بفهمید که قرار بوده در خط ۱۵۴۳۶ چه اتفاقی بیافتد (در این حد که در زبانی مثل پاسکال شاید مجبور باشید ۱۰۰۰ خط قبل و بعد از آن را بررسی کنید تا بفهمید! ولی نگران نباشید، قرار نیست شما برنامه‌نویس پاسکال باشید!). ولی در هنگام برنامه‌نویسی کافی است ۱ میلیونیم آن انرژی را صرف کتید و جلوی آن خط کامنتی بگذارید که قرار است چه اتفاقی بیافتد (به همین سادگی!‌ در مورد انرژی زیاد اغراق نمی‌کنم. در پروژه‌ی خامه‌عسل ما با همین مشکل روبرو هستیم و هنوز هم نتوانستیم خودمان را از این باتلاق بیرون بکشیم!)

در پاسکال کامنت‌ها به دو صورت در کدهای شما قرار می‌گیرند:

(*your comment line 1
Line 2
Line 3
Line 4*)

یا

{your comment line 1
Line 2
Line 3
Line 4}

که تا آن‌جایی که ما فهمیدیم هیچ فرقی با یکدیگر ندارند!


خوب برگردیم سراغ شرط‌های خودمان.

فرض کنید که می‌خواهیم سن کاربرمان را بپرسیم. در مرحله‌ی اول لازم است چک کنیم که کاربر سن‌ش را غلط وارد نکند. پس با فرض این موضوع که در زمان نوح (ع) زندگی نمی‌کنیم بیش‌ترین سن را ۲۰۰ سال و کم‌ترین را ۰ در نظر می‌گیریم. پس برنامه به شکل زیر خواهد بود:

var
age: integer;
ageOK: boolean;
begin
	writeln('plz enter you age:');
	readln(age);
	ageOK:= false;
	if a>0 then
		if a<200 then
			ageOK:= true;
	{do another things}
end.

خوب در برنامه‌ی بالا ما دو شرط را درون هم قرار دادیم. یعنی در کل به این صورت می‌شود که اگر شرط اول درست باشد، پاسکال دستور درون شرط را اجرا می‌کند که از قضا این‌جا یک شرط دیگر است و آن هم اجرا می‌شود و پس از پایان شروط نیز پاسکال به انجام دستورات بعدی ادامه می‌دهد.

دورزدن پاسکال با begin و end; !

اگر متوجه شده‌باشید در دستور پس از if شما اجازه دارید فقط یک دستور را اجرا نمایید و این موضوع مطمئنا مشکل‌زا خواهد بود. برای همین هم ما می‌توانیم با یک «تکه‌‌برنامه» این محدودیت را دور بزنیم. مثلا فرض کنید در برنامه‌ی بالا به کاربر بگوییم که شما که سن‌تان از ۰ کم‌تر است در زمان سفر کرده‌اید یا اگر سن‌شان از ۲۰۰ بیش‌تر است می‌توانند خودشان را به کتاب رتبه‌های سالیانه‌ی گینس معرفی کنند!

پس برنامه به شکل زیر تغییر می‌کند:

var
age: integer;
ageOK: boolean;
begin
	writeln('plz enter you age:');
	readln(age);
	ageOK:= false;
	if a>0 then
	begin
		if a<200 then
		begin
			ageOK:= true;
		end;
		if ageOK=false then
			writeln('The Guinness Book should know you!');
	end;
	if ageOK=false then
	writeln('Did you do time travelling?!? Or did you see Karim Khan Zand?!? ');
	{do another things}
end.

پس ما به‌جای قرار دادن یک دستور، چند دستور را در قالب یک «تکه‌برنامه» قرار دادیم. توجه داشته باشید که طریقه‌ی نوشتن تکه‌برنامه‌ها به صورت خطی است یعنی هر begin با اولین end; پایان می‌یابد و تکه‌برنامه‌ها یکدیگر را قطع نمی‌کنند (یعنی نمی‌شود یک تکه‌برنامه (پسر) داخل یک تکه‌برنامه‌ی دیگر (پدر) آغاز شود ولی پدر قبل از پسر به اتمام برسد {احترامی چیزی گفتن!})

البته این برنامه، برنامه‌ی بزرگی شد چون هنوز مبحث بعدی را نیاموخته‌ایم!

انجام کاری در صورت درست نبودن شرط

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

برای انجام کاری در صورت درست نبودن شرط باید از کلیدواژه‌ی else استفاده کرد. ساختار کلی if – else به شکل زیر است:

if {if statement} then
begin
	{do something}
end;
else
begin
	{do something}
end;

پس حالا برنامه‌ای که نوشتیم به شکل زیر در می‌آید:

var
	age: integer;
	ageOK: boolean;
begin
	writeln('plz enter you age:');
	readln(age);
	ageOK:= false;
	if a>0 then
	begin
		if a<200 then
		begin
			ageOK:= true;
		end;
		else
			writeln('The Guinness Book should know you!');
	end;
	else
		writeln('Did you do time travelling?!? Or did you see Karim Khan Zand?!?');
	{do another things}
end.

که از برنامه‌ی قبلی جمع‌وجورتر است.

خوب با این اوصاف ما می‌توانیم برنامه‌ای چندمنظوره برای کاربر بسازیم. یعنی در ابتدا یک منو چاپ کنیم و به کاربر اجازه دهیم تا از بین گزینه‌های موجود یکی را انتخاب کند. مثلا برنامه‌ی زیر می‌تواند مثال مناسب و انعطاف‌پذیری باشد {برنامه‌ای جامع برای همه‌ی سلیقه‌ها!}

var
	menu: integer;
begin
	writeln('Hi, Welcome to my beautiful user friendly application designed for 2013 uesrs!');
	writeln('Please chose one the items below:');
	writeln('- Press 1 for Do job 1');
	writeln('- Press 2 for Do job 1');
	writeln('- Press 3 for Do job 1');
	writeln('- Press 4 for Do job 1');
	writeln('- or Press anything else to close this beautiful application');
	writeln('I"m waiting …');
	readln(menu)
	if menu=1 then
	begin
		{Do Job 1}
	end;
	if menu=2 then
	begin
		{Do Job 2}
	end;
	if menu=3 then
	begin
		{Do Job 3}
	end;
	if menu=4 then
	begin
		{Do Job 4}
	end;
	writeln('I"m Happy you used my beautiful user friendly application!');
	writeln('Have a good time');
	writeln('Good Bye!');
	readln();
end.

خوب فکر نمی‌کنم نیازی به توضیح داشته‌باشید {اگر در مورد نوشته‌های انگلیسی نیاز به توضیح دارید در دیدگاه بیان کنید!} پس بهتر است تا دیر نشده به سراغ مبحث بعدی برویم {الان ساعت ۲:۱۳ بامداد!}

کدهای چرخشی

در مواقعی شما نیاز دارید تا کاری را چندبار انجام دهید. مثلا بخواهید نمره‌ی ۲۰ نفر را از کاربر بگیرید و میانگین آن‌ها را برای آن‌ها چاپ کنید {این مثال واقعا تکراری بود! فکر کنم هر کتاب آموزشی را که باز کنید این مثال را بتوانید تویش پیدا کنید!} یا کارهای جالب‌تر مثلا چاپ یک مثلث متساوی‌الساقین ستاره‌ای به ساق ۲۰ خط {از این کارها هم انجام می‌دهیم! کمی صبر کنید} مطمئنا استفاده از کپی و پیست {مثلا ۲۰ تا readln بنویسیم!} ، روش جالبی برای گرفتن ورودی (نمرات) یا چاپ خروجی (یک مثلث نسبتا بزرگ!) نخواهد بود.

 این‌جاست که چرخش‌ها یا Loopها به کمک شما می‌آیند.

for

می‌توان گفت for معمول‌ترین دستور چرخشی در زبان‌های برنامه‌نویسی است. در دستور for ما یک شمارنده داریم و یک هدف و از مقدار اولیه‌ی شمارنده یکی‌یکی به آن اضافه می‌کنیم و در هر بار اضافه‌کردن به شمارنده، یک بار دستوری که قرار است اجرا شود را اجرا می‌کنیم {نگران نباشید. ما قرار نیست این کار را انجام دهیم. پاسکال خودش این کار را برای ما انجام می‌دهد!}

چون در دستور for ما نیاز به یک متغیر به عنوان شمارنده داریم، فرض می‌کنیم که متغیر i در ابتدای برنامه تعریف شده است. پس ساختار for به شکل زیر خواهد بود:

for i:=0 to 100 do
	{do something}

یا اگر بخواهیم پاسکال را دور بزنیم به شکل زیر در خواهد آمد:

for i:=0 to 100 do
begin
	{do something}
end;

ساختار چینش درختی برنامه

اگر دقت کرده باشید در برنامه‌هایی که در بالا مثال زدیم هروقت که دستورات به‌عنوان فرزند دستورات دیگری بودند از یک Tab (یا ۸ تا اسپیس) استفاده کردیم. این ساختار به خواناتر شدن کد کمک بسیاری می‌کند و به کسی که کد را می‌خواند کمک می‌کند تا راحت‌تر آن را درک کنند. به شما پیشنهاد می‌کنیم که شما هم در کدهایتان از این ساختار استفاده کنید.

البته زیاد لازم نیست زحمت بکشید. فقط محیط ویرایشگر پاسکال بلد نیست خودش کدها رو مرتب کنه. چند وقت دیگه که وارد سی‌پلاس‌پلاس و سی‌شارپ شدیم دیگه در این مورد مشکلی نخواهیم داشت چون هزار ماشاالله همه‌ی محیط‌های جدید در جهت راحتی و تنبلی برنامه‌نویس‌ها کار می‌کنند و کم مونده ازشون درخواست کنیم که کد رو برامون بنویسند! البته الانش هم همین کامپایلرها یه‌جورایی دارن برامون کدها رو می‌نویسن. {داستان اسمبلی رو که یادتون نرفته؟!؟}


خوب بهتره بحث for رو ادامه بدیم.

به رسم اکثر آموزش‌ها اول برنامه‌ی میانگین رو به عنوان مثال در این‌جا قرار می‌دیم:

var
	now: integer;
	avg: real;
	i: integer;
begin
	readln(now);
	avg:=now;
	for i:=1 to 19 do
	begin
		readln(now);
	end;
	avg:=avg/20;
	writeln(avg);
end.

خوب در برنامه‌ی بالا for را تا ۱۹ رفتیم چون یکی از نمره‌ها را قبلا از کاربر گرفته‌بودیم. توجه داشته باشید که حتی می‌توان تعداد ورودی‌ها را نیز از کاربر گرفت. یعنی لزومی ندارد که نقاط شروع و پایان for را از قبل تعیین کنیم و می‌توانیم آن‌ها را نیز به کاربر بسپاریم.

حالا می‌خواهیم مثلثی مثل مثلث زیر چاپ کنیم

*
**
***
****
*****
******

برای این‌کار لازم است از یک for تو در تو استفاده کنیم. به این معنی که درون یک for، یک for دیگر قرار دهیم.

برای جالب‌تر شدن نیز تعداد خطوط را به کاربر می‌سپاریم {در هنگام نگارش این سطور یعنی ساعت ۲:۵۱ بامداد نویسنده کمی خوابش میاید. اگر برنامه کم‌نمک یا پرنمک بود ببخشید!}

var
	i,j,n: integer;
begin
	writeln('Welcome to my wonderful mathematical application.');
	writeln('You are here and want me to draw a triangle for you!');
	writeln('So I"m waiting for you to give me length of it"s leg …');
	readln(n);
	for i:=1 to n do
	begin
		for j:=1 to I do
			write('*');
		writeln();
	end;
	writeln('I finished drawing. Don"t forget to pay me otherwise I will not draw any other things for you! :X');
	writeln('Honestly there are a lot of consumers waiting for me to draw things for them!');
end.

و خوب فکر می‌کنم برنامه نیاز به توضیح ندارد. فقط این‌که for  پدر در برنامه‌ی ما نقش اشاره‌گر خط را بازی می‌کرد و با هر حرکت آن یک خط رسم می‌شد و به همین دلیل نیز در انتهای دستورات آن writeln() مشاهده می‌شود (برای این‌که در خروجی به خط بعدی برویم!). {ساعت ۳ بامداد است. ادامه‌اش برای فردا!}

تا نشده‌ست آن تمام

{صبح بخیر!} بعد از for پرکاربرد ترین دستور چرخشی while است. مفهوم کلی آن این است که تا وقتی که یک شرط صحیح است کاری را انجام بده. مثلا منوی کاربرپسند (User Friendly!) که با if نوشتیم اگر تنها یک بار اجرا شود کاربردی ندارد (برای هر ابزار برنامه باید دوباره اجرا شود. مثل این‌که کاربر برنامه‌های جداگانه‌ی مختلف را اجرا کند) ولی اگر کاربر بتواند ابزارهای مختلف را استفاده کند و هروقت که خواست خارج شود مثلا ۰ را بزند، برنامه‌ی ما کاربرپسندتر می‌شود!

 پس برنامه‌ی کاربرپسندمان را این‌طور ویرایش می‌کنیم:

var
	menu: integer;
	mCheck: integer;
begin
	writeln('Hi, Welcome to my beautiful user friendly application designed for 2013 uesrs!');
	mCheck:= true;
	while mCheck do
	begin
		writeln('Please chose one the items below:');
		writeln('- Press 1 for Do job 1');
		writeln('- Press 2 for Do job 1');
		writeln('- Press 3 for Do job 1');
		writeln('- Press 4 for Do job 1');
		writeln('- or Press anything else to close this beautiful application');
		writeln('I"m waiting …');
		readln(menu)
		if menu=1 then
		begin
			{Do Job 1}
			continue;
		end;
		if menu=2 then
		begin
			{Do Job 2}
			continue;
		end;
		if menu=3 then
		begin
			{Do Job 3}
			continue;
		end;
		if menu=4 then
		begin
			{Do Job 4}
			continue;
		end;
		mCheck:= false;
	end;
	writeln('I"m Happy you used my beautiful user friendly application!');
	writeln('Have a good time');
	writeln('Good Bye!');
	readln();
end.

continue و break، دو دستور کاربردی برای کنترل چرخش‌ها

گاهی اوقات لازم است که ما اجرای دستورات چرخش را متوقف کنیم و به چرخش ادامه دهیم و یا کلا از چرخش بیرون بیاییم. مثلا در برنامه‌ی بالا لازم است که پس از این‌که کاری که کاربر تعیین کرده‌است را انجام دادیم، دیگر به کارمان ادامه ندهیم (وگرنه mCheck برابر false می‌شود و حلقه ادامه نمی‌یابد!) برای همین از دستور continue استفاده‌ کردیم.

اما در برنامه‌ی بالا می‌توانستیم به‌جای تعریف یک متغیر اضافی از دستور break استفاده کنیم که نتیجه‌ی نهایی می‌شود برنامه‌ی پایین:

var
	menu: integer;
begin
	writeln('Hi, Welcome to my beautiful user friendly application designed for 2013 uesrs!');
	while true do
	begin
		writeln('Please chose one the items below:');
		writeln('- Press 1 for Do job 1');
		writeln('- Press 2 for Do job 1');
		writeln('- Press 3 for Do job 1');
		writeln('- Press 4 for Do job 1');
		writeln('- or Press anything else to close this beautiful application');
		writeln('I"m waiting …');
		readln(menu)
		if menu=1 then
		begin
			{Do Job 1}
			continue;
		end;
		if menu=2 then
		begin
			{Do Job 2}
			continue;
		end;
		if menu=3 then
		begin
			{Do Job 3}
			continue;
		end;
		if menu=4 then
		begin
			{Do Job 4}
			continue;
		end;
		break;
	end;
	writeln('I"m Happy you used my beautiful user friendly application!');
	writeln('Have a good time');
	writeln('Good Bye!');
	readln();
end.

اعمال منطقی پاسکال

اگر تا حالا فکر می‌کردید که کامپیوتر دنیای درهم و برهمی است اشتباه می‌کردید! بلکه کامپیوتر منطقی‌ترین موجود جهان است {البته از مجموع همه‌ی منطق‌ها چیزهای درهم و برهمی ساخته می‌شوند مثل ویندوز، اینترنت و کلی چیز دیگر! اشتباه نکنید! کامیپوتر منطقی است، اما ما کاملا منطقی نیستیم و این باعث آشوب می‌شد!}

اما خیلی وقت‌ها لازم است که در یک شرط چند گزاره‌ی منطقی را باهم چک کنیم. مثلا در مثالی که برای if آوردیم، خیلی بهتر می‌شد اگر آن شرط تو در تو را در یک شرط بزرگ‌تر جمع آوری کنیم. اما مانند دنیای منطق، این‌جا هم چند عمل‌گر منطقی برای گزاره‌ها وجود دارد که آن‌ها را بررسی می‌کنیم:

and

اگر لازم باشد که هر دو (یا چند) شرط در یک زمان برقرار باشند باید از and استفاده کرد. مثلا برنامه‌ی مثال را می‌توان به شکل زیر نوشت:

var
	age: integer;
	ageOK: boolean;
begin
	writeln('plz enter you age:');
	readln(age);
	ageOK:= false;
	if (a>0) and (a<200) then
		ageOK:= true;
	{do another things}
end.

توجه دقت کنید که حتما از پرانتز () برای جداکردن گزاره‌ها استفاده کنید.

or

گاهی اوقات درست بودن یکی از شروط کافی است. مثلا می‌خواهیم نمرات دانش‌آموز را از طریق ایمیل برای پدر یا مادر او ارسال کنیم {فرستادن ایمیل در پاسکال؟!؟ عمرا!} و ما لیستی داریم که شامل ایمیل دانش‌آموز، ایمیل پدر و ایمیل مادر اوست. پس لازم است که فردی که ایمیل براش ارسال می‌شود پدر یا مادر دانش‌آموز باشد. در این حالت شرط ما به شکل زیر خواهد آمد (فرض می‌کنیم متغیر type مقادیر s (دانش آموز)، f (پدر) و m (مادر) را داشته باشد)

if (type='f') or (type='m') then
	{send mail!}

یا می‌توان از یک راه بهتر استفاده کرد و آن این است که چک کنیم که فرد دانش‌آموز نباشد. پس if ما به شکل زیر خواهد آمد:

if type<>'s' then
	{send email!}

not

اگر بخواهیم برعکس یک گزاره‌ی شرطی را چک کنیم، باید از عملگر not استفاده کنیم. مثلا در مثال بالا «اگر فرد دانش‌آموز نبود» را به شکل زیر هم می‌توان نوشت

if not (type='s') then
	{send email!}

البته در برنامه‌نویسی کاربردی پیشنهاد می‌شود که از حالت اول استفاده کنید. چون در حالت دوم شما دو عمل منطقی روی گزاره انجام می‌دهید (اول گزاره‌ی منطقی true یا false را برمی‌گرداند و سپس آن‌را برعکس می‌کنیم!) که در کارهای واقعی همین باعث مشکلاتی در ساختار برنامه می‌شود {اندک، اندک جمع گردد وانگهی دریا شود. همینا جمع می‌شه بعد برنامه‌تون نیم‌ساعت طول می‌کشه تا یه جمع ساده رو انجام بده!}

عمل‌گرهای مقایسه‌ای

در مثال‌های این بخش از عمل‌گرهای مختلفی در شرایط مختلف استفاده کردیم که بد نیست آن‌ها را نیز توضیح دهیم {در اصل در یک جا جمع‌آوری کنیم برای شب امتحان!} (چون مثال در بالا وجود دارد دیگر آن‌ها را تکرار نمی‌کنیم}

  • تساوی: اگر بخواهیم تساوی بین دو متغیر (یا یک متغیر و یک چیز ثابت) را چک کنیم از علامت = استفاده می‌کنیم.
  • کوچکتر، بزرگتر: برای بررسی کوچکتری و بزرگ‌تری مانند ریاضیات شیرین دوره‌ی ابتدایی {از ابتدایی شروع و تا کنون ادامه دارد!} از < و > استفاده می‌کنیم و اگر بخواهیم بزرگتر مساوی یا کوچکتر مساوی را چک کنیم از <= یا >= استفاده می‌کنیم.
  • نامساوی: برای این چک کنیم که دو عبارت مساوی نباشند باید از <> استفاده کنیم.

خوب در این بخش شروط و چرخش‌ها (حلقه‌ها) را آموختیم. بخش بعدی مفاهیم برنامه‌نویسی به اتمام می‌رسد و وارد برنامه‌نویسی سی‌پلاس‌پلاس می‌شویم {بخش بعدی پاسکال تمام می‌شود! هورا!} تا کمی عملی‌تر برنامه‌نویسی یاد بگیریم.

تمرین‌ها

با تشکر از این‌که تمارین بخش قبلی را حل کردید برای این بخش هم تعدادی تمرین در نظر گرفته‌ایم. اگر احیانا کسی زحمت کشید و هر کدام از تمارین را حل کرد ما هم کمی انگیزه پیدا می‌کنیم و جواب تمرین‌ها را در نوشته‌ای منتشر می‌کنیم {به قول استاد خوب حسابان‌مان :نمی‌خواهید یاد بگیرید اصلا چرا میاد نوشته رو می‌خونید. برید به مامانتون بگید من نمی‌خوام یاد بگیرم برید سیگار فروش شید چرا هی وقت‌تون رو با خوندن این چرت‌وپرت‌ها تلف می‌کنید؟ :دی}

  1. ب.ب.ک (برنامه‌ای بنویسید که) قد دانش‌آموزان را بگیرد (تعداد دانش‌آموزان را نیز کاربر تعیین می‌کند) و میانگین، کوتاه‌ترین و بلند‌ترین قد آن‌ها را چاپ کند.
  2. ب.ب.ک ابتدا دو عدد از کاربر بگیرد و سپس با یک محیط کاربرپسند از او بپرسد که قرار است با آن عددها چه کاری بکند (جمع، صرب، تقسیم، تفریق) و نتیجه را چاپ کند.
  3. برنامه‌ای بنویسید که یک‌سری آدرس صفحات بگیرد و تعداد آن‌هایی که از سایت دو برنامه‌نویس هستند را چاپ کند.

پی‌نوشت: اگر مشکلی دارید می‌توانید در دیدگاهی مشکل خود را بیان کنید و یا اگر بخشی از این آمورش نادرست است لطفا اطلاع دهید {متشکرم!}

یک نکته‌ی مهم {سوال انحرافی}: در مثال‌های بالا (در کدهای بالا) اشتباه در دو مثال تکرار شده (راهنمایی یک کلید‌واژه اشتباها به‌عنوان متغیر استفاده شده) آیا می‌توانید آن را بیابید؟

آموزش برنامه‌نویسی – بخش نخست : مفاهیم کلی‌ برنامه‌نویسی


سری جدیدی از آموزش‌های برنامه‌نویسی آغاز شده است. این سری منقضی شده است. پیشنهاد می‌کنیم این سری را ادامه ندهید!


در بخش قبل در مورد زبان‌های برنامه‌نویسی توضیحاتی دادیم. بهتر است سراغ بخش عملی کار برویم!

 در نظر داریم برای شروع آموزش از زبان پاسکال استفاده کنیم که ساخت‌یافته‌ترین زبان برنامه‌نویسی است.

 برای کامپایل کدهای پاسکال نیاز به کامپایلر و محیط برنامه‌نویسی FreePascal دارید. پس از دانلود آن کافی است آن را اجرا کنید و کدهای‌ خود را در محیط آبی‌رنگ برنامه‌ بنویسید. (محیط‌های نرم‌افزاری که برای کدنویسی به کار می‌روند SDK یا Software Development Kit نامیده می‌شوند.)

برنامه (یا همان کد)

به تمام نوشته‌هایی که معمولا در SDK می‌نویسید و بعدا کامپایل خواهند شد برنامه یا کد می‌گویند. در پاسکال روال اصلی برنامه پس از دستور Begin شروع می‌شود و در End. پایان می‌یابد. پس می‌توان گفت ساده‌ترین برنامه در پاسکال به شکل زیر است:

 

هر دستور در پاسکال با یک ; (نقطه‌ویرگول انگلیسی) پایان می‌یابد و نوشتن ; در انتهای دستور اجباری است در غیر این‌صورت کامپایلر هنگام کامپایل برنامه دچار مشکل خواهد شد!

چاپ یک نوشته‌ی ساده

راحت‌ترین کاری که می‌توانیم در برنامه‌نویسی انجام دهیم چاپ یک نوشته‌ی ساده است. برای چاپ نوشته می‌توانیم از دستور Write یا Writeln استفاده کنیم. تفاوت Write با Writeln این است که در دستور Writeln پس از نوشته‌شدن نوشته‌ی موردنظر اشاره‌گر متن یک خط به پایین نیز می‌رود به عبارت دیگر مثل این است که پس از نوشتن متن یک اینتر در ویرایشگر بزنیم (در اصل Writeln خلاصه‌شده‌ای از واژه‌ی WriteLine است). به عنوان مثال در برنامه‌ی

 

خروجی به شکل

 

خواهد بود ولی اگر به‌جای Write از Writeln استفاده می‌کردیم خروجی به شکل

 

ورودی‌های قابل‌قبول برای دستور Write یا Writeln

این دستور (از این به‌ بعد Write و Writeln را یک دستور در نظر می‌گیریم) می‌تواند سه‌نوع ورودی بپذیرد که در ادامه آن‌ها را توضیح می‌دهیم:

1.  متن ساده: اگر می‌خواهید متنی در خروجی چاپ کنید (مانند مثال بالا) باید متن خود را درون کوتیشن «’» قرار دهید تا متن موردنظر مستقیما در خروجی چاپ شود.

2.  عبارت ریاضی: می‌توانید نتیجه‌ی حاصل عبارات ریاضی شامل چهار عمل اصلی را در خروجی به کمک این تابع چاپ کنید. قوائد حاکم در اولویت عملگرها (ضرب، تقسیم، جمع، تفریق) مانند قوائد ریاضی است و تفاوتی نمی‌کند

3.  متغیرها: در مورد متغیرها در آینده صحبت خواهیم‌کرد.

متغیرها

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

متغیرها خانه‌هایی از حافظه‌ی موقت شما (RAM یا Random Access Memory) هستند که برنامه‌ی شما می‌تواند اطلاعاتی را در آن‌ها ذخیره کند. در این‌جا لازم است کمی وارد بحث تئوری-تاریخی شویم.

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

 این کار دردسرهای فراوانی به همراه داشته مثلا خالی‌کردن حافظه‌ای که مورد نیاز نبوده برای افزایش فضای خالی و یا این که هر چیزی که در حافظه ذخیره می‌شده چند خانه از حافظه را اشغال می‌کرده و اطلاعات باید از کدام خانه‌ی حافظه شروع شوند و …

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

 نوع متغیر‌ها

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

متغیرها در پاسکال

مسلما برای استفاده از متغیرها در پاسکال باید ابتدا آن‌ها را تعریف کنیم. در پاسکال متغیرها در پاسکل باید قبل از شروع برنامه تعریف شوند. متغیرها پس از کلیدواژه Var تعریف می‌شوند. برای تعریف آن‌ها از ساختار زیر استفاده می‌کنیم:

 

که ابتدا نام متغیر و پس از : نوع آن را تعیین می‌کنیم (نقطه‌ویرگول فراموش نشود!)

کامپایلر پاسکال در محیط DOS اجرا می‌شود و بنابراین معماری آن ۱۶ بیتی است. در معماری ۱۶ بیتی هر متغیر عدد دو بایت (۱۶ بیت) فضا اشغال می‌کند

 نوع متغیر

متغیرها در پاسکال انواع مختلفی دارند که برای شروع چندتایی از آن‌ها را به شما معرفی می‌کنیم.

  • عدد صحیح: برای ذخیره‌سازی اعداد صحیح می‌توانید از نوع integer استفاده کنید. کامپایلر پاسکال در محیط DOS اجرا می‌شود و بنابراین معماری آن ۱۶ بیتی است. در معماری ۱۶ بیتی هر متغیر عددی دو بایت (۱۶ بیت) فضا اشغال می‌کند بنابر این حداکثر مقدار برای آن در صورتی که فقط از اعداد طبیعی استفاده کنیم ۶۵۵۳۶ است (۰ جزو اعداد طبیعی نیست) بنابراین نوع integet می‌تواند بازه‌ی -۳۲۷۶۸ تا ۳۲۷۶۸ را شامل شود. (۱۵ بیت برای عدد و ۱ بیت برای علامت آن!)
  • عدد حقیقی: برای اعداد حقیقی از نوع real استفاده کنید. این متغیر بر اساس پلت‌فرمی که با آن برنامه‌ می‌نویسید ۴ یا ۸ بایت فضا اشغال می‌کند و می‌تواند بازه‌ی -۲.۹ ۱۰۳۹ تا ۱.۷ × ۱۰۳۸  را شامل شود.
  • رشته‌ی متنی: برای ذخیره‌سازی متن‌ها می‌توانید از نوع string بهره بگیرید. این نوع ۱۰ بایت فضا اشغال می‌کند.
  • مقدار بولین (Boolean) : برای ذخیره‌سازی مقدار درست (true) یا غلط (false) به‌کار می‌رود.
  • یک کارکتر: برای ذخیره‌سازی یک کارکتر مثل ‘a’ یا ‘2’ و یا کارکترهای ASCII دیگر استفاده می‌شود.

و انواع دیگری نیز وجود دارند که بعدا به آن‌ها می‌پردازیم.

دریافت یک ورودی از کاربر

برای دریافت ورودی از کاربر نیاز است که ابتدا متغیری برای آن ورودی در نظر بگیریم. به عنوان مثال در برنامه‌ی زیر

 

  1. ابتدا متغیر a را از نوع عددی تعریف می‌کنیم
  2. سپس به کمک دستور readln از کاربر مقداری می‌گیریم و آن را در a می‌ریزیم(readln این کارها را برای‌مان انجام می‌دهد)
  3. به کمک دستور writeln مقدار گرفته‌شده را چاپ می‌کنیم.
  4. دستور readln() برای این به کار می‌رود تا پس از چاپ متغیر a از برنامه‌ خارج نشویم بلکه برنامه منتظر بماند تا ما کلید اینتر را فشار دهیم. به این منظور که نتیجه‌ی نهایی را ببینیم و کامروا از برنامه خارج شویم!

توجه در این برنامه درصورتی که کاربر مقداری غیر از مقدار عددی وارد کند برنامه خارج می‌شود!

تابع read و readln

این دو تابع که تفاوت‌شان این است که در read فقط اولین کارکتری که کاربر وارد می‌کند خوانده می‌شود ولی در readln تمام‌ کارکترهایی که وارد می‌شود تا قبل از زدن دکمه‌ی اینتر در متغیر ریخته می‌شود، برای گرفتن ورودی از کاربر به کار می‌روند و به صورت readln({varName}); به کار می‌روند. و همان‌طور که اشاره کردیم می‌توان readln را بدون متغیر نیز استفاده کرد و در این صورت ورودی‌های کاربر در جایی ذخیره نمی‌شوند.

تعیین مقدار برای متغیر

شما می‌توانید مقدار متغیرهای‌تان را به‌صورت دستی نیز تنظیم کنید. برای این‌کار از varName:=Value; استفاده می‌شود. مثال زیر را در نظر بگیرید:

 

  1. ابتدا متغیرهای a و b را تعریف کرده‌ایم (نکته‌: برای تعریف چند متغیر از نوع یکسان می‌توان نام‌های آن‌ها را با , ازهم جدا کرد و سپس نوع آن‌ها را نوشت (مثل بالا))
  2. سپس a را از کاربر گرفته‌ایم.
  3. b را برابر با a قرار داده‌ایم.
  4. سپس b را چاپ کرده‌ایم.
  5. با کمک عبارات ریاضی مقدار b را تغییر داده‌ایم و سپس آن را چاپ کرده‌ایم.
  6. در دستور writeln از عبارات ریاضی همراه با متغیرها استفاده کرده‌ایم و مقدار دیگری را چاپ کرده‌ایم.
  7. از readln() برای مشاهده‌ی نتیجه استفاده کرده‌ایم.

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

نوبت شما

بد نیست شما هم کمی جست‌وجو کنید و سوالات زیر را حل کنید. پاسخ‌های خود را نیز در دیدگاه‌ قرار دهید(خواهشا در عجوبه، استک‌اورفلو و یا هر سایت پرسش‌وپاسخ در این زمینه سوال مطرح نکنید! (مطمئنا امتیاز منفی می‌گیرید!)). پاسخ صحیح را در بخش بعدی منتشر خواهیم کرد!

  1. ب.ب.ک (برنامه‌ای بنویسید که) دو متغیر از نوع string ار کاربر گرفته و آن‌ها را باهم جمع کند و چاپ کند.
  2. ب.ب.ک میانگین حقیقی دو عدد صحیح را چاپ کند. (a,b:integer; avg:real;)
  3. ب.ب.ک نام کاربر و سن او را گرفته و آی‌دی به صورت نام‌+سن چاپ کند (name:string; age:integer;)

آموزش برنامه‌نویسی – بخش صفرم: برنامه‌نویسی چیست!


سری جدیدی از آموزش‌های برنامه‌نویسی آغاز شده است. این سری منقضی شده است. پیشنهاد می‌کنیم این سری را ادامه ندهید!


بنابر وعده‌ای که داده بودیم آموزش برنامه‌نویسی را آغاز می‌کنیم. دوست دارم در ابتدا در مورد برنامه‌نویسی و زبان‌های برنامه‌نویسی و نکاتی این‌چنینی توضیح دهم و سپس وارد بخش فنی کار شوم.

 کارت‌پانچ از اولین ابزارهایی بوده که دانشمندان به وسیله‌ی آن با پردازنده ارتباط برقرار می‌کردند. با توجه به این‌که راحت‌ترین واحد ارتباط با یک مدار الکترونیکی قطع یا وصل کردن جریان است مبنای شمارش و دستورات در پردازنده هم بر پایه ۰ (قطع‌بودن جریان) و ۱ (وصل‌بودن جریان) تعریف شده است و تا امروز هم مبنای شمارش در کامپیوتر بیت (۰ یا ۱) است و به همین ترتیب واحد‌های بایت (۸ بیت) کیلوبایت(۱۰۲۴ بایت در مبنای ویندوز و ۱۰۰۰ بایت در مبنای لینکوس) و … تعریف می‌شود.

 کارت‌پانچ نیز برای ارتباط با پردازنده از وجود سوراخ در مکان‌های مشخص استفاده می‌کند و وجود آن ۱ و وجود‌نداشتن آن ۰ را معنی می‌دهد. هر پردازنده می‌تواند تعداد دستورات مشخصی (که معمولا توان ۲ هستند) را انجام دهد و اجتماع این دستورات می‌تواند نتیجه‌ی مخصوصی داشته باشد. اما برای یک هدف مشخص تعداد زیادی از این دستورات لازم است و به همین دلیل استفاده از کارت‌پانچ کار سختی بوده و درصد خطا را به شدت افزایش می‌داده.

 

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

 مثلا پردازشگرهای عادی قابلیت پردازش مستقیم ۲۵۶ دستور را دارند که البته جز در حالت بیتی (یا همان صفر و یکی) می‌توان از دستورات نوشتاری مثل ADD نیز برای برنامه‌نویسی اسمبلی استفاده کرد ولی در هر حال ریسک بالایی دارد چون دستورات اسمبلی مستقیما در پردازشگر پردازش می‌شوند و قدرت تخریب صد درصد هریک از منابع سیستم را نیز دارا می‌باشند.‌

 پردازنده‌ها فقط توانایی پردازش داده‌ها به‌صورت ۰ و ۱ را دارند و در واقع هریک از دستورات متنی اسمبلی هم به کد ۸ بیتی متناظر خود تبدیل و در نهایت ذخیره‌ می‌شود تا در زمان لازم اجرا شود و به همین دلیل است که در زبان اسمبلی تنها ۲۵۶ (۲۸) دستور داریم و مسلما نوشتن یک نرم‌افزار فقط به زبان اسمبلی تقریبا غیرممکن است و سرمایه بسیار عظیم و دقت بسیار زیادی نیاز دارد! و به همین دلیل زبان‌های برنامه‌نویسی متولّد شدند.

 پردازشگر نمی‌تواند مستقیما کدهایی را که به زبان یکی از زبان‌های برنامه‌نویسی است را پردازش کند (در بالا توضیح دادم که کدهای متنی اسمبلی هم به ۰ و ۱ تبدیل می‌شوند و مستقیما به صورت متنی در فایل‌های اجرایی ذخیره نمی‌شوند بعلاوه ساختار نوشتاری کدهای برنامه‌نویسی به زبان‌های غیر اسمبلی به زبان معمول ما نزدیک‌تر است و تعداد دستورات بیش‌تری دارند) به همین دلیل نیاز به برنامه‌ای داریم که کدهای نوشته‌شده را به ۰ و ۱ تبدیل و ذخیره کند تا قابل اجرا شدن باشند. به این نرم‌افزار کامپایلر (Compiler) گفته می‌شود و کدهای نوشته‌شده کامپایل (Compile) می‌شوند.

 البته یک‌سری از کدهایی که به برخی از زبان‌ها مانند JavaScript ، PHP، Flash(البته زبان برنامه‌نویسی فلش ActionScript است و در نسخه‌های جدیدتر فلش کامپایل می‌شوند) و … به‌جای کامپایل، تفسیر (Interpret) می‌شوند. به این معنی که به جای این‌که مستقیما به فایل‌های بیتی (صفر و یکی) تبدیل شوند، در قالب نرم‌افزاری دیگر اجرا می‌شوند. به این‌ نرم‌افزارها تفسیرگر (Interpreter) گفته می‌شود. و اجراشدن این کدها به این صورت است که برنامه‌ی اجرا کننده آن‌ها را خط‌به‌خط می‌خواند و اجرا می‌کند و به همین دلیل هم اجرا شدن آن‌ها کندتر از برنامه‌هایی است که کامپایل می‌شوند. (به همین دلیل هم PHP و ASPکلاسیک کندتر از ASP.Net هستند – این‌ها موضوعاتی است که در آینده به آن‌ها خواهیم پرداخت)

 ویکی‌پدیا در مورد زبانی‌که تفسیر می‌شود می‌گوید

زبانی‌که تفسیر می‌شود زبانی است که نرم‌افزار به‌صورت «غیر مستقیم» توسط تفسیرگر اجرا می‌شود («تفسیر» می‌شود) این زبان با زبانی که کامپایل می‌شود در تضاد است چون زبانی که کامپایل می‌شود ابتدا به کدماشین (کد اسمبلی) تبدیل می‌شود و سپس در پردازشگر میزبان اجرا می‌شود.

از لحاظ تئوری هر زبانی هم می‌تواند زبانی باشد که کامپایل می‌شود و هم زبانی که تفسیر می‌شود بنابراین این‌که زبانی کامپایل می‌شود یا تفسیر صرفا با استفاده‌ی معمول‌ای که از یک زبان می‌شود تأیین می‌شود و نه هویت آن زبان.  در واقع از نظر عملکرد تفاوت‌هایی در تفسیرشدن یا کامپایل‌شدن یک زبان خاص از نظر روش و کارایی وجود دارد.

زبان‌های زیادی توسط کامپایلر‌ها و تفسیرگرها اجرا شده‌اند. مثل بیسیک، سی، Lisp، پاسکال و پایتون در حالی که جاوا به شکلی تبدیل می‌شود که در نظر گرفته‌شده تا تفسیر شود. اغلب کامپایل در لحظه (Just-In-Time compilation یا JIT) برای تولید کد ماشین (یا همان کد اسمبلی) استفاده می‌شود. زبان‌های برنامه‌نویسی دات‌نت‌فریم‌ورک مایکروسافت همیشه به زبان سطح میانی (Common Intermediate Language، IL یا CIL) کامپایل می شوند و سپس این کدها در زمان اجرا، در لحظه کامپایل می‌شوند.

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

در بخش بعدی آموزش زبان برنامه‌نویسی پاسکال را قرار می‌دهیم تا کمک آن مفاهیم کلی برنامه‌نویسی را توضیح دهیم.

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

دوره‌های آموزش برنامه‌نویسی، تصمیم نهایی

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

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

 نکته‌ی پایانی این‌که با توجه به این‌که دیدگاه‌های در نوشته‌ی قبلی کمک به‌سزایی در تصمیم‌گیری داشته از این‌که دیدگاه‌تان را بیان‌کنید خوشحال می‌شویم.

زکات علم آموزش‌دادن آن است

سلام

همانطور که می‌دانید زکات علم آموزش‌دادن آن است. من هم دوست دارم یه دوره برای شروع برنامه‌نویسی از اول این‌جا شروع کنم (احتمالا پاسکال->سی‌پلاس‌پلاس->سی‌شارپ->تکنولوژی‌های تحت پلت‌فورم‌ دات‌نت) اما قبلش دوست دارم نظر سنجی کنم که آیا موافق هستید که این دوره شروع بشه یا نه؟

دیدگاه‌تان را بیان کنید!