آموزش PHP (فصل ۴)


  string(2) "C#"
}

می‌بینیم بدون آنکه Key (کلید) برای اعضای این آرایه در نظر بگیریم، به صورت خودکار کلیدها در نظر گرفته شده‌اند.به خاطر داشته باشیدنکته‌ای که در مورد Array در تمامی زبان‌های برنامه‌نویسی وجود دارد این است که شمارش خانه‌ها در آرایه‌ها به جای ۱، از ۰ آغاز می‌گردد مگر آنکه خود دولوپر بخواهد تا شمارش از ۱ شروع شود. این نکته‌ای است که اگر به آن توجه نشود ممکن است دولوپرهای تازه‌کار را در ابتدای راه سردرگم سازد.

در تفسیر آرایهٔ فوق، بایستی بگوییم که آرایه‌ای داریم از جنس Indexed (عددی) که دارای ۴ عضو یا اِلِمان است و مقدار اعضای آن هم از جنس استرینگ (رشته) هستند. حال آرایه فوق را به صورت زیر تغییر می‌دهیم:

$array = array(0 => 'PHP', 1 => 'Java', 2 => 'Python', 3 => 'C#');

توجه داشته باشید که برای اختصاص یک Value (مقدار)‌ به یک Key (کلید) در آرایه‌ها در زبان PHP هرگز نمی‌بایست از علامت = استفاده کرد بلکه علائم <= برای این منظور به کار می‌روند. اگر مجدد خروجی بگیریم، می‌بینیم که هیچ تفاوتی در خروجی مشاهده نمی‌شود. اگر هم بخواهیم که شمارش اندیس‌ها از عدد ۱ شروع شود، اندیس‌ها را به صورت زیر از عدد ۱ شروع می‌کنیم:

<?php
$array = array(1 => 'PHP', 2 => 'Java', 3 => 'Python', 4 => 'C#');
var_dump($array);

به عنوان خروجی داریم:

array(4) {
  [1]=>
  string(3) "PHP"
  [2]=>
  string(4) "Java"
  [3]=>
  string(6) "Python"
  [4]=>
  string(2) "C#"
}

به عنوان مثالی هم از آرایه‌های به اصطلاح Associative داریم:

<?php
$array = array('firstname' => 'Behzad', 'lastname' => 'Moradi', 'dob' => 1984, 'marital_status' => true, 'political_preference' => null);
var_dump($array);

ابتدا خروجی را بررسی کرده سپس به ارائهٔ توضیحات بیشتر می‌پردازیم:

array(5) {
  ["firstname"]=>
  string(6) "Behzad"
  ["lastname"]=>
  string(6) "Moradi"
  ["dob"]=>
  int(1984)
  ["marital_status"]=>
  bool(true)
  ["political_preference"]=>
  NULL
}

همان‌طور که می‌بینیم، این آرایه دارای ۵ آیتم است و این در حالی است که کلیدها یا اندیس‌های این آرایه عددی نبوده بلکه از جنس استرینگ هستند و به همین دلیل این نوع آرایه‌ها را اصطلاحاً Associative می‌نامند.

نکتهٔ مهمی که در مورد کلیدهای آرایه‌های Indexed و Associative وجود دارد این است که در مورد آرایه‌های Indexed، اندیس‌ها حتماً بایستی عددی بوده و تحت هیچ عنوان داخل علائم ” ” یا ‘ ‘ قرار نمی‌گیرند اما در مورد آرایه‌های Associative -همان‌طور که در مثال فوق مشاهده می‌شود- اندیس‌ها چون استرینگ هستند، داخل علائم ” ” یا ‘ ‘ قرار گرفته‌اند.

نکتهٔ دیگری که در مورد آرایه‌ها وجود دارد این است که ما می‌توانیم داده‌های مختلفی را داخل اعضای مختلف هر آرایه ذخیره سازیم. به طور مثال، در آرایهٔ فوق در اندیس‌های firstname و lastname از مقدار استرینگ استفاده کرده‌ایم، در اندیس dob (تاریخ تولد) از مقدار عددی، در اندیس marital_status (وضعیت تأهل) از مقدار بولینی و در نهایت در اندیس political_preference (گرایش سیاسی) از مقدار null استفاده کرده‌ایم (در مورد آرایه‌های Indexed هم دقیقاً می‌توان از داده‌های مختلف استفاده کرد). نکتهوقتی از ()var_dump برای نمایش محتویات یک آرایه استفاده می‌کنیم -همان‌طور که در خروجی مشاهده می‌شود- تایپ (نوع) مقدار هر اندیس در معرض دیدمان قرار می‌گیرد. 

دسترسی به اعضای آرایه‌های Indexed و Associative
همان‌طور که از دستورات echo و print برای چاپ مقادیر متغیرها تاکنون استفاده می‌کردیم، نمی‌توانیم برای چاپ آرایه‌ها استفاده کنیم! به طور مثال، اگر آرایهٔ فوق را به صورت زیر بخواهیم چاپ کنیم:

<?php
$array = array('firstname' => 'Behzad', 'lastname' => 'Moradi', 'dob' => 1984, 'marital_status' => true, 'political_preference' => null);
echo $array;

با ارور یا بهتر بگوییم هشدار زیر مواجه خواهیم شد:

Notice: Array to string conversion in /var/www/sokanacademy-php-course/04/04-arrays/index.php on line 3
Array

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

به منظور چاپ کلیهٔ آیتم‌های یک آرایه باید از ساختار Loop (حلقه) استفاده کرد که در آموزش‌های آتی به تفصیل مورد بحث قرار خواهد گرفت اما اگر بخواهیم صرفاً یکی از آیتم‌های یک آرایه -خواه Indexed و خواه Associative- را نمایش دهیم، می‌بایست از ساختار زیر استفاده کنیم:

<?php
$array = array('firstname' => 'Behzad', 'lastname' => 'Moradi', 'dob' => 1984, 'marital_status' => true, 'political_preference' => null);
echo $array['dob'];

به عنوان خروجی اسکریپت فوق، ۱۹۸۴ چاپ خواهد شد. در واقع، برای دستیابی به هر کدام از اندیس‌های آرایه که بخواهیم، صرفاً نیاز است تا نام آرایه را نوشته سپس یک جفت علائم [ ] را قرار دهیم. حال اگر آرایه از جنس Associative بود، می‌بایست استرینگ مد نظر را وارد کنیم (در مثال فوق استرینگ ‘dob’ را در نظر گرفته‌ایم) و اگر هم آرایه از جنس Indexed بود، صرفاً عدد مد نظر را وارد می‌کنیم. در مثال فوق، اگر بخواهیم یکی از خانه‌های آرایه را داخل یک استرینگ به نمایش در آوریم، می‌توانیم از علائم ” ” استفاده کنیم:

echo "My date of birth is $array['dob']";

چنانچه اسکریپت فوق را اجرا کنیم، با ارور زیر مواجه خواهیم شد:

Parse error: syntax error, unexpected '' (T_ENCAPSED_AND_WHITESPACE), expecting identifier (T_STRING) or variable (T_VARIABLE) or number (T_NUM_STRING) in /var/www/sokanacademy-php-course/04/04-arrays/index.php on line 3

برای رفع این مشکل، می‌بایست از علائم { } در دو طرف آرایه استفاده کنیم:

echo "My date of birth is {$array['dob']}";

و به عنوان خروجی خواهیم داشت:

My date of birth is 1984

برای دستیابی به آیتم‌های یک آرایه از جنس Indexed هم به صورت زیر عمل می‌کنیم:

<?php
$array = array('PHP', 'Java', 'Python', 'C#');
echo $array[2];

در حقیقت، یک آرایه از جنس Indexed داریم و قصد داریم آیتم Python را چاپ کنیم؛ برای این منظور، اندیس ۲ را داخل علائم [ ] نوشته‌ایم (گرچه در ظاهر Python اِلِمان سوم است، اما می‌دانیم که شمارش خانه‌ها در آرایه از صفر آغاز می‌شود؛ به عبارت دیگر، PHP می‌شود آیتم صفرم، Java می‌شود آیتم یکم، Python می‌شود آیتم دوم و #C می‌شود آیتم سوم). اگر هم بخواهیم اندیس فوق را داخل یک استرینگ نمایش دهیم، می‌توانیم از ساختار زیر استفاده کنیم:

<?php
$array = array('PHP', 'Java', 'Python', 'C#');
echo "$array[2] is a nice language";

به عنوان خروجی داریم:

Python is a nice language

می‌بینیم که اطراف آرایهٔ مد نظر از علائم { } استفاده نکردیم و خروجی هم به درستی نمایش داده شد. در واقع، زمانی که اندیس‌های آرایه از جنس استرینگ (Associative) باشند، آرایه را باید داخل علائم { } قرار داد.

راه‌کار جایگزین فانکشن ()array به منظور ساخت آرایه در زبان PHP
تاکنون دیدیم که با استفاده از تابع از پیش‌ تعریف شده‌ای در زبان PHP تحت عنوان ()array به چه شکل می‌توان دست به ساخت آرایه‌ها زد. واقعیت امر آن است که امروزه در اکثر فریمورک‌ها از علائم [ ] برای ساخت آرایه‌ها استفاده می‌شود و کاربرد ()array کمتر و کمتر شده است. برای روشن‌تر شدن نحوهٔ کاربرد [ ]، آرایهٔ فوق را به شکل زیر ریفکتور می‌کنیم:

$array = ['PHP', 'Java', 'Python', 'C#'];

به نظر می‌رسد که استفاده از علائم [ ] به مراتب راحت‌تر از استفاده از فانکشن ()array باشد (از اینجای آموزش به بعد، این روش را برای ساخت آرایه‌ها استفاده خواهیم کرد). هشداربه خاطر داشته باشید که [ ] از نسخهٔ ۵.۴ به بالا ساپورت می‌شود؛ لذا اگر قصد کار کردن روی پروژه‌ای قدیمی را دارید، بهتر است که از همان فانکشن ()array استفاده نمایید.

حال با دانستن اینکه با استفاده از علائم [ ] می‌توان دست به ساخت یک آرایه زد، آرایهٔ فوق را می‌توان به شکل زیر بازنویسی کرد:

<?php
$array[0] = 'PHP';
$array[1] = 'Java';
$array[2] = 'Python';
$array[3] = 'C#';

و این در حالی است که نتیجهٔ هر دو آرایه یکسان است.

آپدیت کردن یا افزودن اندیس جدید به یک آرایه
به راحتی این امکان در اختیار دولوپرهای زبان برنامه‌نویسی PHP قرار گرفته تا مقدار یکی از اندیس‌های آرایه را آپدیت کرده و یا اندیس/مقدار جدید به آرایه اضافه کنند. برای مثال داریم:

<?php
$array[0] = 'PHP';
$array[1] = 'Java';
$array[2] = 'Python';
$array[3] = 'C#';
$array[1] = 'C++'; // Index 1 is updated
var_dump($array);

در حقیقت اگر این اسکریپت را در مرورگر اجرا کنیم، خواهیم دید که مقدار اندیس ۱ که در ابتدا برابر بود با استرینگ Java، آپدیت شده و مقداری همچون ++C برایش در نظر گرفته شده است. برای افزودن یک اندیس/مقدار جدید به انتهای آرایه هم از ساختار زیر استفاده می‌کنیم:

<?php
$array[0] = 'PHP';
$array[1] = 'Java';
$array[2] = 'Python';
$array[3] = 'C#';
$array[] = 'C++'; // Index 4 is added
var_dump($array);

به عنوان خروجی داریم:

array(5) {
  [0]=>
  string(3) "PHP"
  [1]=>
  string(4) "Java"
  [2]=>
  string(6) "Python"
  [3]=>
  string(2) "C#"
  [4]=>
  string(3) "C++"
}

در حقیقت، اگر نام آرایه را نوشته و علائم [ ] را مقابل آن قرار دهیم بدون اینکه هیچ اندیسی در نظر بگیریم، مقدار مد نظر به انتهای آرایه افزوده شده و اندیس هم به صورت خودکار یک واحد افزایش می‌یابد. این قضیه در مورد آرایه‌هایی از نوع اصطلاحاً Associative هم کاملاً صادق است:

<?php
$array = array('firstname' => 'Behzad', 'lastname' => 'Moradi', 'dob' => 1984, 'marital_status' => true, 'political_preference' => null);
$array['firstname'] = 'Sahand';
$array['occupation'] = 'Developer';
var_dump($array);

به عنوان خروجی داریم:

array(6) {
  ["firstname"]=>
  string(6) "Sahand"
  ["lastname"]=>
  string(6) "Moradi"
  ["dob"]=>
  int(1984)
  ["marital_status"]=>
  bool(true)
  ["political_preference"]=>
  NULL
  ["occupation"]=>
  string(9) "Developer"
}

می‌بینیم که در ابتدا کلید firstname برابر با Behzad بود اما پس از ویرایش مقدار جدید Sahand برایش در نظر گرفته شده است؛ همچنین یک اندیس جدید تحت عنوان occupation با مقدار استرینگ Developer هم اضافه شده که در خروجی می‌بینیم به انتهای آرایه افزوده شده است.

آشنایی با ساختار حلقهٔ foreach در زبان PHP


در آموزش گذشته دیدیم که با استفاده از اندیس‌ها، به چه شکل می‌توانستیم به تک‌تک خانه‌های یک آرایه دست پیدا کنیم اما این در حالی است که گاهی‌اوقات ما نیاز داریم تا کلیهٔ خانه‌های (اعضای) یک آرایه را در اختیار داشته و در معرض دید کاربر قرار دهیم که برای این منظور بایستی با مفهوم Loop (لوپ یا حلقه) آشنا شویم. به طور کلی، در زبان PHP انواع مختلفی لوپ وجود دارد که عبارتند از:
– foreach
– for
– while
– do while

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

آشنایی با حلقهٔ foreach در زبان PHP
در زبان PHP ساختاری تحت عنوان foreach وجود دارد که به منظور دستیابی به تمامی اِلِمان‌های یک آرایه مورد استفاده قرار می‌گیرد. ساختار کلی foreach به صورت زیر است:

foreach ($array as $key => $value) {
    // Do something with $value.
}

همان‌طور که مشاهده می‌شود، حلقهٔ foreach آرایه‌ای همچون array$ را به عنوان پارامتر ورودی می‌گیرد؛ سپس کلیدواژه‌ای تحت عنوان as که به صورت پیش‌فرض در این زبان تعریف شده را نوشته و نام‌هایی دلخواه برای اندیس‌ها و مقادیرشان در نظر می‌گیریم (در این مثال، از متغیر key$ برای ذخیره‌سازی کلید یا اندیس و از متغیر value$ برای ذخیره‌سازی مقدار استفاده شده است). نکته‌ای که در ارتباط با لوپ زدن روی یک آرایه وجود دارد این است که می‌توان صرفاً مقادیر را چاپ کرد. به عبارت دیگر:

foreach ($array as $value) {
    // Do something with $value.
}

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

همچنین توجه داشته باشید که چنانچه تصمیم گرفتید تا هم اندیس‌ها و هم مقادیر را از آرایهٔ مد نظر استخراج کنید، مابین متغیری که قرار است اندیس را در خود ذخیره سازد با متغیری که قرار است مقدار آن اندیس را در خود ذخیره سازد از علامت <= استفاده نمایید. هشدارهمواره توصیه می‌شود که از نام‌های بامسمی برای ذخیره‌سازی اندیس‌ها و مقادیر استفاده شود. به طور مثال اگر فرض کنیم که آرایه‌ای داریم تحت عنوان users$ که حاوی دیتای مرتبط با کاربران وب‌سایت است و قصد داریم با استفاده از یک لوپ به اطلاعات تک‌تک کاربران دست یابیم، بهتر است از متغیری تحت عنوان userId$ برای ذخیره‌سازی کلید و userInfo$ به منظور ذخیره‌سازی اطلاعات مرتبط با هر شناسه استفاده کرد.

برای روشن‌تر شدن کاربرد عملی حلقه‌ها، آرایه‌ای به صورت زیر را مبنا قرار داده، سپس با استفاده از یک لوپ اقدام به چاپ تک‌تک اعضای آن آرایه می‌کنیم:

<?php
$array = ['PHP', 'Java', 'Python', 'C#'];
foreach ($array as $key => $value) {
    echo $key . ' is ' . $value . '<br>';
}

خروجی این اسکریپت برابر است با:

0 is PHP
1 is Java
2 is Python
3 is C#

در تفسیر کدهای فوق بایستی بگوییم که آرایه‌ای ساخته‌ایم تحت عنوان array$ که حاوی نام تعدادی از زبان‌های برنامه‌نویسی محبوب است؛ سپس با استفاده از یک حلقهٔ foreach قصد داریم تا تک‌تک اعضای این آرایه را با استفاده از دستور echo چاپ کنیم. برای این منظور، متغیرهای key$ و value$ را نوشته و در نهایت از یک تگ <br> استفاده کرده تا هر عضو در خطی مجزا چاپ شود.

در حقیقت، foreach این وظیفه را دارا است تا آن‌قدر در آرایهٔ array$ بچرخد و اعضای آن را چاپ کند تا اینکه دیگر هیچ چیزی داخل آرایه باقی نمانده باشد. همان‌طور که قبلاً اشاره شد، همچنین می‌توانیم به سادگی اندیس‌ها را از خروجی حذف کرده و صرفاً مقادیر را مد نظر قرار دهیم:

<?php
$array = ['PHP', 'Java', 'Python', 'C#'];
foreach ($array as $value) {
    echo $value . '<br>';
}

به عنوان خروجی داریم:

PHP
Java
Python
C#

استفاده از دستورات شرطی در داخل لوپ‌ها
گاهی‌اوقات بسته به Business Logic وب اپلیکیشن خود، نیاز داریم تا شرط‌های خاصی را داخل لوپ‌ها اعمال کنیم که این کار در زبان PHP به سادگی امکان‌پذیر است (منظور از این اصطلاح کاربرد واقعی نرم‌افزار است). به عنوان مثال داریم:

<?php
$array = ['PHP', 'Java', 'Python', 'C#'];
foreach ($array as $value) {
    if ($value == 'Java') {
        continue;
    }
    echo $value . '<br>';
}

و خروجی اسکریپت فوق برابر است با:

PHP
Python
C#

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

<?php
$array = ['PHP', 'Java', 'Python', 'C#'];
foreach ($array as $value) {
    if ($value == 'Python') {
        break;
    }
    echo $value . '<br>';
}

به عنوان خروجی اسکریپت فوق داریم:

PHP
Java

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

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

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Date Form</title>
    </head>
    <body>
        <form>
            <?php
                $days = range(1, 31);
                $months = [1 => 'January', 2 => 'February', 3 => 'March', 4 => 'April', 5 => 'May', 6 => 'June', 7 => 'July', 8 => 'August', 9 => 'September', 10 => 'October', 11 => 'November', 12 => 'December'];
                $years = range (2018, 2028);
            ?>
            <select name="day">
                <?php
                    foreach ($days as $day) {
                        echo "<option value='$day'>$day</option>";
                    }
                ?>
            </select>
            <select name="month">
                <?php
                    foreach ($months as $monthKey => $month) {
                        echo "<option value='$monthKey'>$month</option>";
                    }
                ?>
            </select>
            <select name="year">
                <?php
                    foreach ($years as $year) {
                        echo "<option value='$year'>$year</option>";
                    }
                ?>
            </select>
        </form>
    </body>
</html>

چنانچه اسکریپت فوق را از طریق لوکال‌هاست در مرورگر باز کنیم، می‌بینیم که فرمی در اختیار ما قرار گرفته که با استفاده از آن می‌توانیم روز، ماه و سال مد نظر خود را انتخاب کنیم. چنانچه به سورس این صفحه نگاه کنیم صرفاً کدهای HTML می‌بینیم، اما این در حالی است که مقادیر تگ‌های select به صورت کاملاً دینامیک (پویا) و با استفاده از زبان PHP ایجاد شده‌اند.

آنچه در اسکریپت فوق نیاز به توضیح دارد این است که داخل تگ‌ form تگ‌های آغازین و پایانی پی‌اچ‌پی را ایجاد کرده و داخل آن‌ها سه آرایه تحت عناوین months ،$days$ و years$ ایجاد کرده‌ایم. 

در اینجا بایستی با یکی از توابع از پیش تعریف شده در زبان PHP تحت عنوان ()range آشنا شد. کاری که این فانکشن انجام می‌دهد این است که بر اساس نقطهٔ آغازین (پارامتر اول) و نقطهٔ پایانی (پارامتر دوم)، آرایه‌ای شامل طیفی از اعداد را برایمان ایجاد می‌کند که ترتیب آن‌ها از کوچک به بزرگ است. به طور مثال، در متغیر days$ طیفی از اعداد ۱ تا ۳۱ ایجاد شده و داخل این متغیر ذخیره می‌شود (به همین منوال، طیفی از سال ۲۰۱۸ تا ۲۰۲۸ را در متغیر years$ ذخیره کرده‌ایم).

در متغیر months$ هم آرایه‌ای از ماه‌های میلادی را ایجاد کرده‌ایم اما از آنجا که اندیس‌های آرایه در زبان PHP به صورت پیش‌فرض از عدد صفر شروع می‌شود، اندیس‌گذاری را هم خود به صورت دستی از عدد یک شروع کرده‌ایم چرا که به طور مثال، به عنوان عدد مرتبط با ماه January به عدد یک نیاز داریم نه صفر.

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

برخلاف تگ‌های مرتبط با روز و سال که صرفاً به مقادیر نیاز داشتیم، در تگ مرتبط با ماه از دو متغیر به نام‌های monthKey$ و month$ به ترتیب برای نشان دادن معادل عددی ماه‌ها و معادل الفبایی ماه‌ها استفاده کرده‌ایم. حال نگاهی به خروجی صفحهٔ فوق می‌اندازیم:

<!DOCTYPE html>
<html>
   <head>
      <meta charset="utf-8">
      <title>Date Form</title>
   </head>
   <body>
      <form>
         <select name="day">
            <option value='1'>1</option>
            <option value='2'>2</option>
            <option value='3'>3</option>
            <option value='4'>4</option>
            <option value='5'>5</option>
            <option value='6'>6</option>
            <option value='7'>7</option>
            <option value='8'>8</option>
            <option value='9'>9</option>
            <option value='10'>10</option>
            <option value='11'>11</option>
            <option value='12'>12</option>
            <option value='13'>13</option>
            <option value='14'>14</option>
            <option value='15'>15</option>
            <option value='16'>16</option>
            <option value='17'>17</option>
            <option value='18'>18</option>
            <option value='19'>19</option>
            <option value='20'>20</option>
            <option value='21'>21</option>
            <option value='22'>22</option>
            <option value='23'>23</option>
            <option value='24'>24</option>
            <option value='25'>25</option>
            <option value='26'>26</option>
            <option value='27'>27</option>
            <option value='28'>28</option>
            <option value='29'>29</option>
            <option value='30'>30</option>
            <option value='31'>31</option>
         </select>
         <select name="month">
            <option value='1'>January</option>
            <option value='2'>February</option>
            <option value='3'>March</option>
            <option value='4'>April</option>
            <option value='5'>May</option>
            <option value='6'>June</option>
            <option value='7'>July</option>
            <option value='8'>August</option>
            <option value='9'>September</option>
            <option value='10'>October</option>
            <option value='11'>November</option>
            <option value='12'>December</option>
         </select>
         <select name="year">
            <option value='2018'>2018</option>
            <option value='2019'>2019</option>
            <option value='2020'>2020</option>
            <option value='2021'>2021</option>
            <option value='2022'>2022</option>
            <option value='2023'>2023</option>
            <option value='2024'>2024</option>
            <option value='2025'>2025</option>
            <option value='2026'>2026</option>
            <option value='2027'>2027</option>
            <option value='2028'>2028</option>
         </select>
      </form>
   </body>
</html>

می‌بینیم که به چه سادگی توانستیم با استفاده از زبان PHP کدهای HTML را به صورت دینامیک (پویا) تولید کنیم. دانلود فایل‌های تمرین

آشنایی با آرایه‌های Multidimensional (چندبُعدی) در زبان PHP


در مبحث معرفی آرایه‌ها گفتیم که مقادیر یک آرایه می‌تواند دیتاتایپ‌های مختلفی همچون استرینگ، بولین، عدد و … باشد؛ لازم به ذکر است که به عنوان Value یک آرایه می‌توان از آرایه‌ای دیگر نیز استفاده کرد که در چنین مواقعی ما با یک آرایهٔ به اصطلاح Multidimensional (چندبُعدی) سروکار داریم. برای درک بهتر ساختار یک آرایهٔ چندبُعدی در زبان PHP، ابتدا آرایه‌ای حاوی اعداد فرد می‌سازیم:

$odds = [1, 3, 5];

سپس آرایهٔ دیگری تحت عنوان evens$ می‌سازیم که قرار است تعداد عدد زوج را در خود ذخیره سازد:

$evens = [2, 4, 6];

حال آرایهٔ دیگری می‌سازیم تحت عنوان both$ که مقادیرش برابر با آرایه‌هایی است که قبلاً تعریف کرده‌ایم:

<?php
$odds = [1, 3, 5];
$evens = [2, 4, 6];
$both = [$odds, $evens];
var_dump($both);

با استفاده دستور ()var_dump، مقادیر آرایهٔ both$ را پرینت می‌کنیم:

array(2) {
  [0]=>
  array(3) {
    [0]=>
    int(1)
    [1]=>
    int(3)
    [2]=>
    int(5)
  }
  [1]=>
  array(3) {
    [0]=>
    int(2)
    [1]=>
    int(4)
    [2]=>
    int(6)
  }
}

همان‌طور که ملاحظه می‌شود، آرایه‌ای داریم حاوی دو اندیس (0 و 1) که هر کدام از آن‌ها نیز حاوی سه عضو هستند. اصطلاحاً به چنین آرایه‌ای Multidimensional (چندبُعدی) گفته می‌شود که کاربردهای فراوانی در پیاده‌سازی پروژه‌های وب اپلیکیشن با زبان PHP دارا است.

دستیابی به اعضای یک آرایهٔ Multidimensional
به منظور دستیابی به اعضای یک آرایهٔ چندبُعدی، به راحتی می‌تواند شمارهٔ اندیس را فراخوانی کرد:

var_dump($both[0]);

اگر هم بخواهیم اولین اندیس از اندیس ۰ را به دست آوریم، به سادگی به صورت زیر عمل می‌کنیم:

var_dump($both[0][0]);

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

کار با آرایه‌های چندبُعدی با استفاده از حلقهٔ foreach در زبان PHP


امروزه کمتر اپلیکیشنی را می‌توان یافت که در پیاده‌سازی آن از آرایه‌های چندبُعدی استفاده نشده باشد و وب اپلیکیشن‌ها هم از این قاعده مستثنی نیستند. در همین راستا، در این آموزش قصد داریم ببینیم که به چه شکل می‌توان در زبان PHP با استفاده از حلقهٔ foreach به کار آرایه‌های چندبُعدی پرداخت. برای این منظور، فایلی می‌سازیم تحت عنوان index.php و کدهای زیر را داخل آن می‌نویسیم:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Multidimensional Arrays</title>
    </head>
    <body>
        <?php
            $countries = [
                'Iran' => [
                    'Yazd',
                    'Ilam',
                    'Sistan Balochestan'
                ],
                'Denmark' => [
                    'North Zealand',
                    'Fyn',
                    'North Jutland'
                ]
            ]
        ?>
        <h1>Total No of Countries Is: <?= count($countries) ?></h1>
        <?php
            foreach($countries as $country => $provinces) {
                echo "<h3>$country includes:</h3>";
                foreach($provinces as $province) {
                    echo "<li>$province</li>";
                }
            }
        ?>
    </body>
</html>

چنانچه این فایل را اجرا کنیم و به سورس صفحه نگاهی بیندازیم، با خروجی زیر مواجه خواهیم شد:

<!DOCTYPE html>
<html>
   <head>
      <meta charset="utf-8">
      <title>Multidimensional Arrays</title>
   </head>
   <body>
      <h1>Total No of Countries Is: 2</h1>
      <h3>Iran includes:</h3>
      <li>Yazd</li>
      <li>Ilam</li>
      <li>Sistan Balochestan</li>
      <h3>Denmark includes:</h3>
      <li>North Zealand</li>
      <li>Fyn</li>
      <li>North Jutland</li>
   </body>
</html>

همان‌طور که می‌بینیم، هیچ اثری از کدهای PHP نیست و صرفاً خروجی را به زبان HTML مشاهده می‌کنیم. حال در تفسیر کدهای فوق، باید بگوییم که ابتدا آرایه‌ای تحت عنوان countries$ ساخته‌ایم که چندبُعدی است بدین شکل که این آرایه دو کلید (Key) اصلی دارد تحت عناوین Iran و Denmark و این در حالی است که هر کدام از این کلیدها خود آرایه‌ای هستند که حاوی سه زیرشاخه‌اند.

در ادامه، با استفاده از فانکشن از پیش تعریف شده‌ای در زبان PHP تحت عنوان ()count که این وظیفه را دارا است تا تعداد کلیدهای یک آرایه را شمارش کند، در خط بیست و دومم اقدام به چاپ تعداد کل کشورهایی که در این آرایه قرار دارند کرده‌‌ایم که برابر با ۲ است.

سپس با استفاده از یک حلقهٔ foreach، اقدام به تفکیک آرایهٔ countries$ به اجزایش کرده‌ایم بدین شکل که Key و Value ذخیره شده در این آرایه را به ترتیب در متغیرهایی تحت عناوین country$ و provinces$ ذخیره کرده‌ایم. در خط بیست و پنجم، ابتدا نام کشور را چاپ کرده‌ایم و در ادامه هم با استفاده از یک foreach دیگر، اجزای زیرشاخهٔ هر کشور را به دست آورده‌ایم. به عبارت دیگر، در foreach دوم استان‌های هر کشور که در متغیر provinces$ ذخیره کرده بودیم را تک به تک در متغیری تحت عنوان province$ ذخیره کرده سپس مقدار این متغیر را داخل تگ‌های <li></li> که برای ساخت لیست در زبان HTML استفاده می‌شوند، قرار داده‌ایم. 

می‌بینیم که به چه سادگی می‌توان به داده‌های ذخیره شده در آرایه‌های چندبُعدی دست یافت. به همین منوال، می‌توان ابعاد آرایه را به مراتب بیشتر کرد که برای روشن‌تر شدن این مسئله، کدهای فوق را به صورت زیر ریفکتور می‌کنیم:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Multidimensional Arrays</title>
    </head>
    <body>
        <?php
            $countries = [
                'Iran' => [
                    'Yazd' => [
                        'Meybod',
                        'Ardekan',
                        'Hamidia'
                    ],
                    'Ilam' => [
                        'Dehloran',
                        'Ivan',
                        'Abdanan'
                    ],
                    'Sistan Balochestan' => [
                        'Zabol',
                        'Iranshahr',
                        'Chabahar'
                    ]
                ],
                'Denmark' => [
                    'North Zealand' => [
                        'Egedal',
                        'Fredensborg',
                        'Frederikssund'
                    ],
                    'Fyn' => [
                        'Assens',
                        'Faaborg',
                        'Kerteminde'
                    ],
                    'North Jutland' => [
                        'Frederikshavn',
                        'Thisted',
                        'Aalborg'
                    ]
                ]
            ]
        ?>
        <h1>Total No of Countries Is: <?= count($countries) ?></h1>
        <?php
            foreach($countries as $country => $provinces) {
                echo "<h3>$country includes:</h3>";
                foreach($provinces as $province => $cites) {
                    echo "<li>$province</li>";
                    foreach($cites as $city) {
                        echo "- $city <br>";
                    }
                }
            }
        ?>
    </body>
</html>

و به عنوان خروجی هم خواهیم داشت:

<!DOCTYPE html>
<html>
   <head>
      <meta charset="utf-8">
      <title>Multidimensional Arrays</title>
   </head>
   <body>
      <h1>Total No of Countries Is: 2</h1>
      <h3>Iran includes:</h3>
      <li>Yazd</li>
      - Meybod <br>- Ardekan <br>- Hamidia <br>
      <li>Ilam</li>
      - Dehloran <br>- Ivan <br>- Abdanan <br>
      <li>Sistan Balochestan</li>
      - Zabol <br>- Iranshahr <br>- Chabahar <br>
      <h3>Denmark includes:</h3>
      <li>North Zealand</li>
      - Egedal <br>- Fredensborg <br>- Frederikssund <br>
      <li>Fyn</li>
      - Assens <br>- Faaborg <br>- Kerteminde <br>
      <li>North Jutland</li>
      - Frederikshavn <br>- Thisted <br>- Aalborg <br>
   </body>
</html>

آنچه به کد اضافه کرده‌ایم این است که برای هر استان سه شهر زیرشاخه در نظر گرفته‌ایم و با استفاده از foreach سوم، به تک‌تک شهرهای قرار گرفته داخل هر استان دست یافته‌ایم و می‌بینیم که به چه سادگی می‌توان در زبان PHP آرایه‌های چند لایه تعریف کرد. دانلود فایل‌های تمرین

استفاده از آرایه‌ها در فرم‌های HTML


در طراحی فرم، گاهی‌اوقات پیش می‌آید که نیاز داریم تا از تگ‌های select یا checkbox استفاده کنیم که در چنین شرایطی برای گرفتن کلیهٔ مقادیر ورودی توسط کاربر، نیاز داریم تا دیتای فرم خود را در قالب یک آرایه ذخیره کرده و در سمت سرور نیز این آرایه را به هر شکلی که بخواهیم پردازش کنیم.

آشنایی با نحوهٔ ذخیره‌سازی دیتای select در آرایه
پیش از هر چیز، فایلی تحت عنوان select.php ساخته و کدهای زیر را داخل آن قرار می‌دهیم (البته لازم به ذکر است که این نام کاملاً دلبخواه است):

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Select</title>
    </head>
    <body>
        <form action="select.php" method="POST">
            <select name="langs[]" multiple="multiple">
                <option value="PHP">PHP</option>
                <option value="Java">Java</option>
                <option value="Python">Python</option>
            </select>
            <input type="submit" name="btn" value="Submit">
        </form>
    </body>
</html>

در تفسیر کدهای فوق باید گفت که یک صفحهٔ سادهٔ HTML داریم که داخل آن فرمی قرار دارد که حاوی یک تگ select است. آنچه به عنوان مقدار اتریبیوت name این تگ خودنمایی می‌کند، استفاده از علائم [ ] پس از نام انتخابی برای این تگ (langs) است که این علائم حاکی از آنند که مقادیر بایستی در قالب یک آرایه ذخیره شوند (نیاز به توضیح هم نیست که اتریبیوت multiple نیز این امکان را به ما می‌دهد تا در آن واحد چندین گزینه را با هم انتخاب کنیم).

مقدار در نظر گرفته شده برای اتریبیوت action هم نام فایلی است که قرار است دیتای فرم را پردازش کند تحت عنوان handle-form.php به طوری که پس از کلیک کردن روی دکمه، دیتای فرم به این فایل ارجاع داده می‌شود.

حال برای هَندل کردن این داده‌ها، فایلی تحت عنوان handle-form.php می‌سازیم و کدهای PHP مربوطه را می‌نویسیم:

<?php
if ($_SERVER['REQUEST_METHOD'] == 'POST') {
    $languages = $_POST['langs'];
    var_dump($languages);
    die;
}

در خط دوم از یک دستور شرطی استفاده کرده‌ایم که پیش از هر چیز چک می‌کند ببیند آیا این فرم واقعاً Submit (ارسال) شده است یا خیر؛ اگر دیتای فرم ارسال نشده بود که هیچ اتفاقی رخ نمی‌دهد و در غیر این صورت، کدهای قرار گرفته داخل دستور شرطی if عملی خواهند شد.

پیش از این با آرایهٔ سوپرگلوبال SERVER_$ آشنا شدیم. یکی از کلیدهای این آرایه REQUEST_METHOD نام دارد که مشخص‌کنندهٔ مِتدی است که ریکوئست (درخواست) به سمت سرور ارسال شده است. در حقیقت، همان‌طور که در فرم خود مقدار اتریبیوت method را برابر با POST قرار دادیم، حال چک می‌کنیم ببینیم که آیا REQUEST_METHOD برابر با POST است یا خیر.

در خط سوم هم متغیری ساخته‌ایم تحت عنوان languages$ که این وظیفه را دارا است تا مقادیر کلید langs که داخل آرایهٔ گلوبال POST_$ پس از ارسال فرم ذخیره شده را در خود نگاه دارد. در نهایت هم آرایهٔ languages$ را داخل تابع ()var_dump قرار داده تا بتوانیم محتوایات داخل آن را مشاهده کنیم.

پس از اجرای این فایل از طریق لوکال‌هاست، می‌بینیم که یک فرمی در معرض‌ دیدمان قرار دارد که می‌توانیم از طریق آن یکی از گزینه‌های Java ،PHP و Python و یا هر سهٔ آن‌ها را انتخاب کنیم و روی دکمهٔ Submit کلیک کنیم (دلیل اینکه می‌توان هر سه را انتخاب کرد، اختصاص اتریبیوت multiple به تگ select است). جهت تست، گزینه‌های PHP و Python را انتخاب کرده و روی دکمه کلیک می‌کنیم:

array(2) {
  [0]=>
  string(3) "PHP"
  [1]=>
  string(6) "Python"
}

می‌بینیم که آرایه‌ای داریم حاوی دو Value (مقدار) که دقیقاً همان مواردی هستند که داخل فرم انتخاب کردیم. اکنون قصد داریم از داخل فرم HTML، علائم [ ] که پس از نام langs قرار داده بودیم را حذف کنیم و تست کنیم ببینیم نتیجه چه تغییری می‌یابد:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Select</title>
    </head>
    <body>
        <form action="handle-form.php" method="POST">
            <select name="langs" multiple="multiple">
                <option value="PHP">PHP</option>
                <option value="Java">Java</option>
                <option value="Python">Python</option>
            </select>
            <input type="submit" name="btn" value="Submit">
        </form>
    </body>
</html>

در خط نهم می‌بینیم نام [ ]langs را به langs تغییر دادیم. حال مجدد همان گزینه‌های PHP و Python را انتخاب کرده و روی دکمه کلیک می‌کنیم:

string(6) "Python"

می‌بینیم علیرغم اینکه ما دو گزینه را انتخاب کردیم، اما گزینهٔ آخر (Python) انتخاب شده و دیتاتایپ آن هم استرینگاست! به عبارت دیگر، چنانچه بخواهیم دیتای یک تگ select را در قالب یک آرایه به سمت سرور ارسال نماییم، حتماً باید از علائم [ ] پس از نام دلخواهی که برای اتریبیوت name در نظر می‌گیریم، استفاده نماییم.

 آشنایی با نحوهٔ ذخیره‌سازی دیتای checkbox در آرایه
برای این منظور، فایلی تحت عنوان checkbox.php یا هر نام دلخواه دیگری ساخته و کدهای زیر را داخل آن قرار می‌دهیم:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Checkbox</title>
    </head>
    <body>
        <form action="handle-form.php" method="POST">
            <input type="checkbox" name="langs[]" value="PHP"> PHP<br>
            <input type="checkbox" name="langs[]" value="Java"> Java<br>
            <input type="checkbox" name="langs[]" value="Python"> Python<br>
            <input type="submit" name="btn" value="Submit">
        </form>
    </body>
</html>

در حقیقت، کدهای فوق سه چک‌باکس در اختیار ما قرار می‌دهند که با تیک زدن آن‌ها، می‌توانیم یکی از زبان‌های Java ،PHP و Python و یا هر سه را انتخاب کنیم. همچون فرم قبلی،‌ مقدار در نظر گرفته شده برای اتریبیوت action هم همان فایل handle-form.php است که پیش از این کدنویسی کردیم که اصلاً نیازی هم به تغییر ندارد.

در زمان طراحی چک‌باکس‌، از همان تگ input استفاده می‌شود با این تفاوت که مقدار اتریبیوت type را برابر باcheckbox قرار می‌دهیم. به هر تعداد چک‌باکس که بخواهیم اضافه کرده و برای اتریبیوت name هم نامی دلخواه + علائم [ ] استفاده می‌کنیم تا کلیهٔ مقادیر در قالب یک آرایه ذخیره شوند (گرچه نام دلخواه است، اما نام انتخابی برای تمامی موارد باید یکسان باشد). جهت تست، هر سه آیتم را تیک زده و روی دکمهٔ Submit کلیک می‌کنیم:

array(3) {
  [0]=>
  string(3) "PHP"
  [1]=>
  string(4) "Java"
  [2]=>
  string(6) "Python"
}

می‌بینیم که گزینه‌های تیک زده شده در قالب یک آرایه ذخیره شدند. حال همچون گذشته علائم [ ] را از کنار نام langs حذف می‌کنیم:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Checkbox</title>
    </head>
    <body>
        <form action="handle-form.php" method="POST">
            <input type="checkbox" name="langs" value="PHP"> PHP<br>
            <input type="checkbox" name="langs" value="Java"> Java<br>
            <input type="checkbox" name="langs" value="Python"> Python<br>
            <input type="submit" name="btn" value="Submit">
        </form>
    </body>
</html>

اکنون مجدد هر سه آیتم را تیک زده و کلیک می‌کنیم:

string(6) "Python"

می‌بینیم که اگر علائم [ ] حذف شوند، همواره آخرین گزینهٔ تیک زده شده (Python) به سمت سرور در قالب یک استرینگ ارسال می‌شود. دانلود فایل‌های تمرین


نحوهٔ استفاده از حلقهٔ for در آرایه‌های PHP


پیش از این با نحوهٔ استفاده از حلقهٔ foreach به منظور دستیابی به اِلِمان‌های یک آرایه در زبان PHP آشنا شدیم؛ اما گفتیم که به غیر از این ساختار، یکسری لوپ (حلقه) دیگر نیز در این زبان تعبیه شده‌اند که با استفاده از آن‌ها می‌توان به اعضای یک آرایه دست یافت که عبارتند از:

– for
– while
– do while

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

for (Initialization; Condition; Step) {
   // Code to be executed
}

همان‌طور که مشاهده می‌شود، for دارای سه پارامتر ورودی است. Initialization (شروع) متغیری است معمولاً از نوع عددی که نقطهٔ شروع یا به عبارتی مقدار اولیهٔ شمارنده را مشخص می‌سازد، Condition (شرط) هم در آغاز هر بار اجرای حلقه چک می‌شود به طوری که اگر True بود حلقه ادامه می‌یابد و در صورتی هم که برابر با False بود، اجرای این حلقه خاتمه خواهد یافت و در نهایت به Step (گام) می‌رسیم که در این گام مقدار متغیر Initialization را با هر مقداری که در نظر داشته باشیم تغییر می‌دهیم اما به یاد داشته باشیم که این تغییر مقدار در پایان هر بار اجرای حلقه صورت می‌گیرد. فلوچارت مرتبط با نحوهٔ اجرای این نوع لوپ به صورت زیر است:

برای روشن‌تر شدن نحوهٔ کارکرد حلقهٔ for، در ادامه مثالی می‌آوریم:

for($i = 1; $i <= 3; $i++) {
    echo "The number is " . $i . "<br>";
}

همان‌طور که مشاهده می‌شود، به جای Initialization یا به عبارتی متغیری که این وظیفه را دارا است تا نقطهٔ شروع حلقه را مشخص کند، متغیری در نظر گرفته‌ایم تحت عنوان i$ با مقدار اولیهٔ ۱ سپس یک علامت ; قرار داده و Condition یا شرطی را نوشته‌ایم که در هر بار اجرای حلقه چک خواهد شد که در این مثال گفته‌ایم مادامی‌ که مقدار متغیر i$ کوچک‌تر یا مساوی با ۳ بود، این حلقه ادامه یابد. مجدد یک علامت ; قرار داده و در نهایت Step را نوشته‌ایم بدین صورت که در هر بار اجرای حلقه، در انتهای اسکریپت یک واحد به متغیر i$ اضافه خواهد شد (علائم ++ منجر به افزایش یک واحد به متغیر عددی i$ خواهد شد.) نیاز به توضیح نیست که داخل حلقه هم اسکریپتی نوشته‌ایم که مقدار متغیر i$ را چاپ می‌کند به طوری که به عنوان خروجی این اسکریپت داریم:

The number is 1
The number is 2
The number is 3

به منظور درک بهتر این ساختار، نحوهٔ اجرای اسکریپت فوق را تفسیر می‌کنیم. در ابتدا متغیری تعریف کرده‌ایم تحت عنوان i$ که مقدار اولیهٔ این متغیر یک عدد صحیح برابر با ۱ است. زمانی که این اسکریپت را اجرا می‌کنیم، شرط در نظر گرفته شده می‌سنجد ببیند که آیا مقدار i$ کوچک‌تر یا مساوی (=>) با عدد ۳ هست یا خیر که اگر جواب این شرط اصطلاحاً Ture (درست) بود، حلقه یک بار اجرا می‌شود و در پایان اسکریپت‌های قرار گرفته داخل این حلقه، یعنی جایی که از دستور echo استفاده کرده‌ایم، پارامتر سوم داخل این حلقه اجرا شده و یک واحد به i$ افزوده می‌گردد و مقدارش برابر با ۲ می‌شود. مجدد شرط بررسی شده و کماکان مقدار True است و حلقه یک بار دیگر می‌چرخد و در پایان اسکریپت مجدد یک واحد به مقدار متغیر i$ اضافه شده و مقدارش برابر با ۳ می‌شود.

در ادامه، وقتی که شرط بررسی می‌شود، می‌بینیم که کماکان True است چرا که علائم => حاکی از آنند که این متغیر باید کوچک‌تر یا مساوی با عدد ۳ باشد که در این مرحله مقدار متغیر i$ برابر با عدد ۳ است؛ به عبارتی، شرط برقرار است و حلقه یک بار دیگر اجرا می‌شود تا اینکه در انتهای اسکریپت مقدار متغیر i$ برابر با ۴ شده که مسلماً شرط False شده و این حلقه خاتمه می‌یابد. در همین راستا، با یک تغییر کوچک در اسکریپت فوق می‌بینیم که شرط هرگز برقرار نشده و حلقه اجرا نمی‌گردد:

for($i = 4; $i <= 3; $i++) {
    echo "The number is " . $i . "<br>";
}

در واقع، از آنجا که مقدار اولیهٔ در نظر گرفته شده برای متغیر i$ برابر با عدد صحیح ۴ است و در شرط هم گفته‌ایم که این مقدار باید کوچک‌تر یا مساوی با عدد ۳ باشد، این شرط هرگز برقرار نشده و اسکریپت ما هم اجرا نخواهد شد.

نکتهٔ دیگری که در ارتباط با پارامتر سوم (Step) باید در نظر گرفت اینکه معمولاً این پارامتر وظیفه دارد تا مقدار متغیر مذکور رو افزایش دهد، اما این در حالی است که در برخی شرایط می‌توان این مقدار را کاهش هم داد. به عنوان مثال داریم:

for($i = 20; $i >= 10; $i--) {
    echo "The number is " . $i . "<br>";
}

به عنوان خروجی هم داریم:

The number is 20
The number is 19
The number is 18
The number is 17
The number is 16
The number is 15
The number is 14
The number is 13
The number is 12
The number is 11
The number is 10

در واقع، در اسکریپت فوق گفته‌ایم مادامی که مقدار متغیر i$ بزرگ‌تر یا مساوی با عدد ۱۰ است، حلقه اجرا شده و در پایان هر بار چرخش هم یک واحد از متغیر i$ کم شود (علائم — حاکی از کم شدن یک واحد از عدد صحیح هستند.) همچنین در پارامتر Step می‌توان عمل ضرب و تقسیم هم انجام داد به طوری که در اسکریپت زیر به راحتی مقدار متغیر مذکور را به توان رسانده‌ایم:

for($i = 1; $i < 70; $i *= 2) {
    echo "The number is " . $i . "<br>";
}

به عنوان خروجی داریم:

The number is 1
The number is 2
The number is 4
The number is 8
The number is 16
The number is 32
The number is 64

در تفسیر اسکریپت فوق بایستی بگوییم که در اولین باری که حلقه اجرا می‌شود، شرط برقرار است چرا که عدد ۱ از ۷۰ کوچک‌تر است. حال پس از اینکه حلقه برای اولین بار اجرا شد، در پایان اجرا مقدار اولیهٔ متغیر i$ که برابر با ۱ بود در عدد ۲ ضرب شده و مجدد داخل همان متغیر i$ ذخیره می‌شود که از این پس مقدار این متغیر می‌شود ۲ = ۱ × ۲ و مسلماً زمانی که شرط چک می‌شود، عدد ۲ از ۷۰ کوچک‌تر بوده و شراط برابر با True خواهد بود و این حلقه اجرا شده بدین شکل که در ادامه مقدار متغیر i$ که از این پس برابر با ۲ است مجدد در عدد ۲ ضرب شده و مقدارش برابر با ۴ می‌شود و این کار ادامه می‌یابد تا جایی که مقدار متغیر i$ بیش از ۷۰ شده و پاسخ شرط اصطلاحاً False می‌گردد.

اختیاری بودن پارامترهای حلقهٔ For
لازم به ذکر است که هر سه پارامتر ورودی این حلقه Optional (اختیاری) هستند. برای مثال:

$noOne = 1;
$noTwo = 5;

for ( ; $noOne <= $noTwo; $noOne++ ) {
  echo "The number is " . $noOne . "<br>";
}

به عنوان خروجی داریم:

The number is 1
The number is 2
The number is 3
The number is 4
The number is 5

در تفسیر اسکریپت فوق بایستی گفت که ابتدا به ساکن دو متغیر تعریف کرده‌ایم تحت عناوین noOne$ و noTwo$ اما این در حالی است که در حلقهٔ for پارامتر اول را درج نکرده‌ایم و صرفاً به بیان Condition و همچنین Step پرداخته‌ایم (البته به خاطر داشته باشید گرچه پارامتر اول نوشته نشده است، اما علامت ; مرتبط با آن می‌بایست گذاشته شود که در غیر این صورت با ارور مواجه خواهید شد.)

همچنین توجه داشته باشید که اگر پارامتر دوم (Condition) حذف گردد، به صورت پیش‌فرض مقدار True برای شرط این حلقه در نظر گرفته خواهد شد و نیاز به توضیح نیست که در چنین شرایطی یک حلقهٔ به اصطلاح Infinite (بی‌پایان) خواهیم داشت. در همین راستا داریم:

for($i = 1; ; $i++) {
    echo "The number is " . $i . "<br>";
}

می‌بینیم که پارامتر وسط، همان پارامتری که مربوط به شرط است، حذف شده است اما کماکان علامت ; سر جایش باقی است. به عنوان خروجی هم داریم:

The number is 1
The number is 2
The number is 3
The number is 4
The number is 5
The number is 6
The number is 7
The number is 8
The number is 9
The number is 10
The number is 11
The number is 12
The number is 13
The number is 14
The number is 15
The number is 16
The number is 17
The number is 18
The number is 19
The number is 20
The number is 21
The number is 22
The number is 23
The number is 24
The number is 25
The number is 26
The number is 27
.
.
.

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

for (; ;) {
    $i = rand(1, 10);
    echo "The number is " . $i . "<br>";
    if ($i == 2) {
        break;
    }
}

به عنوان خروجی داریم:

The number is 4
The number is 1
The number is 7
The number is 6
The number is 1
The number is 3
The number is 2

در حقیقت، سازوکار حلقهٔ فوق بدین صورت است که کلیهٔ پارامترها را حذف نموده و داخل حلقه متغیری تعریف کرده‌ایم تحت عنوان i$ که مقدارش برابر با تابع از پیش‌ تعریف‌شده‌ای در زبان PHP تحت عنوان ()rand است که یک عدد تصادفی تولید می‌کند بدین صورت که دستور داده‌ایم تا این عدد رَندوم در بازهٔ ۱ تا ۱۰ باشد. سپس شرطی در نظر گرفته‌ایم بدین شکل که به محض اینکه مقدار این عدد تصادفی برابر با ۲ شد، از داخل حلقه خارج شویم (دستور break این وظیفه را دارا است تا حلقه را متوقف نماید.)

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

$menu = ['Java', 'Python', 'PHP', 'NodeJS'];
$count = count($menu);
echo "<ul>";
for ($index = 0; $index < $count; $index++) {
    echo "<li><a href='#{$menu[$index]}'>{$menu[$index]}</a></li>";
}
echo "</ul>";

اگر به سورس خروجی اسکریپت فوق نگاه کنیم، خواهیم داشت:

<ul>
    <li><a href='#Java'>Java</a></li>
    <li><a href='#Python'>Python</a></li>
    <li><a href='#PHP'>PHP</a></li>
    <li><a href='#NodeJS'>NodeJS</a></li>
</ul>

در تفسیر اسکریپت فوق بایستی بگوییم آرایه‌ای داریم تحت عنوان menu$ که حاوی نام برخی زبان‌های برنامه‌نویسی است (البته نیاز به توضیح نیست که NodeJS زبان برنامه‌نویسی نیست!) سپس در متغیری تحت عنوان count$ و با استفاده از فانکشن از پیش تعریف‌شده‌ای در زبان PHP به نام ()count تعداد اندیس‌های آرایهٔ menu$ را درآورده‌ایم که برابر است با چهار.

در ادامه، از آنجا که قصد داریم یک منو بسازیم، ابتدا با استفاده از دستور echo تگ آغازین <ul> را چاپ کرده‌ایم؛ سپس با استفاده از حلقه اقدام به چاپ کردن عناصر داخل آرایه نموده‌ایم بدین صورت که شمارنده‌ای تحت عنوان index$ با مقدار اولیهٔ صفر ایجاد کرده، سپس به عنوان شرط این حلقه گفته‌ایم مادامی که مقدار این شمارنده از مقدار متغیر count$ کوچک‌تر بود، این حلقه ادامه یافته و به عنوان پارامتر Step نیز دستور داده‌ایم تا در هر بار Iteration (چرخش) حلقه، یک واحد به مقدار متغیر index$ اضافه گردد.

داخل حلقه هم با استفاده از دستور echo تگ‌های آغازین و پایانی <li></li> را چاپ کرده و برای اینکه آیتم‌های منو لینک باشند، از تگ‌های آغازین و پایانی <a></a> نیز استفاده نموده‌ایم. حال برای چاپ کردن اِلِمان‌های آرایه ابتدا از علائم { } استفاده کرده‌ایم چرا که پیش از این توضیح دادیم زمانی که بخواهیم مقادیری از یک آرایه که اِسترینگ (رشته) هستند را با استفاده از دستور echo چاپ کنیم، می‌بایست از این علائم استفاده نمود؛ سپس نام آرایهٔ مذکور (menu$) را نوشته و داخل علائم [ ] مرتبط با این آرایه، شمارندهٔ index$ را قرار داده‌‌ایم (همچنین به عنوان مقدار اَتریبیوت href تگ <a> نیز یک # قرار داده و نام زمان مد نظر را چاپ کرده‌ایم.)

در حقیقت، زمانی که اسکریپت فوق اجرا می‌شود، در اولین Iteration (چرخش) شرط برقرار خواهد بود چرا که مقدار متغیر index$ که برابر با صفر است از مقدار متغیر count$ که برابر با چهار است کوچک‌تر است؛ لذا دستور echo اجرا شده و اولین لینک از منو (Java) روی صفحه چاپ می‌شود بدین صورت که با نوشتن [menu[$index$ دستور داده‌ایم خانهٔ اول (با اندیس صفر) از آرایهٔ menu$ چاپ شود. سپس یک واحد به مقدار متغیر شمارنده اضافه شده و این کار تا زمانی ادامه می‌یابد تا هر چهار اِلِمان آرایهٔ ما چاپ گردد. در نهایت هم با استفاده از دستور echo تگ پایانی <ul/> را چاپ کرده و منو تکمیل شده است. حال اگر بخواهیم منوی فوق را با تعداد خطوط کمتری بنویسیم، خواهیم داشت:

echo "<ul>";
for ($index = 0, $menu = ['Java', 'Python', 'PHP', 'NodeJS'], $count = count($menu); $index < $count; $index++) {
    echo "<li><a href='#{$menu[$index]}'>{$menu[$index]}</a></li>";
}
echo "</ul>";

در واقع، پارامتر Initialization (شروع) می‌تواند شامل هر تعداد متغیری باشد که مد نظر داریم بدین صورت که آن‌ها را با یک کاما از یکدیگر مجزا سازیم.

استفاده از حلقهٔ For به منظور ایجاد پسورد یا هَش
یکی دیگر از مثال‌های کاربردی استفاده از این نوع لوپ (حلقه)، ساخت پسورد و یا اِسترینگی به عنوان هَش است. فرض کنیم قصد داریم برای کاربران سایت یک پسورد رَندوم هشت‌ کاراکتری بسازیم (و یا مثلاً برای ساخت یک لینک بازیابی رمزعبور، نیاز به یک هَش داریم.) برای این منظور، به سادگی از این حلقه می‌توانیم به صورت زیر استفاده نماییم:

$password = "";
for ($i = 0; $i < 8; $i++) {
    $password .= chr(rand(0, 25) + 97);
}
echo "Your password is: $password";

به عنوان خروجی داریم:

Your password is: zialktrs

و اگر بار دیگر اسکریپت فوق را اجرا کنیم، خواهیم داشت:

Your password is: psarxbtf

می‌بینیم که پسوردها کاملاً رَندوم تولید شده‌اند (البته در عین حال این نکته را هم در نظر داشته باشیم که در شرایط بسیارنادری ممکن است بر حسب تصادف دو پسورد کاملاً یکسان شوند که البته احتمال چنین چیزی بسیار پایین است.)

در تفسیر اسکریپت فوق بایستی بگوییم که ابتدا به ساکن یک متغیر تعریف کرده‌ایم تحت عنوان password$ که خالی است. سپس با استفاده از یک حلقه، دستور داده‌ایم مادامی که مقدار متغیر i$ کمتر از عدد هشت است، این حلقه ادامه یابد. داخل این حلقه هم متغیری که پیش از این تحت عنوان password$ ساختیم را مقداردهی کرده‌ایم بدین صورت که از دو تابع از پیش تعریف شده در زبان PHP تحت عناوین ()rand و ()chr استفاده کرده‌ایم که به نظر می‌رسد تا این مرحله از آموزش به خوبی با کاربرد تابع ()rand آشنا شده باشید؛ لذا می‌پردازیم به کاربرد تابع جدید.

به طور خلاصه، کاربرد تابع ()chr در زبان PHP این است که کاراکتر معادل یک مقدار ASCII را در قالب اِسترینگی تک‌کاراکتری باز می‌گرداند. در مثال فوق، گفته‌ایم که تابع ()rand عددی رِندوم مابین ۰ تا ۲۵ در اختیار ما قرار داده، سپس برای آنکه میزان تصادفی بودن آن را بیشتر کنیم، خروجی را با عدد اختیاری همچون ۹۷ جمع کرده و حاصل‌جمع آن‌ها به عنوان پارامتر ورودی تابع ()chr در نظر گرفته‌ایم که این تابع هم حرف معادل با آن عدد را باز می‌گرداند.

پیش از این با مفهوم Concatenation آشنا شده‌ایم. با در نظر گرفتن این موضوع، در هر بار اجرای حلقهٔ فوق خروجی تابع ()chr را با استفاده از ساختار =. به متغیر password$ الحاق کرده‌ایم (چسبانده‌ایم) تا اینکه در نهایت مقدار این متغیر هشت حرف کاملاً تصادفی خواهد بود.

نحوهٔ استفاده از حلقهٔ while در زبان PHP


جهت یادآوری کاربرد Loop (حلقه) در زبان‌های برنامه‌نویسی، بایستی بگوییم که اساساً از حلقه‌ها زمانی استفاده می‌شود که بخواهیم بلوکی از کد را بارها و بارها اجرا کنیم تا زمانی که شرط خاصی برقرار شده و اجرای اسکریپت متوقف گردد. پیش از این با حلقه‌هایی از جنس foreach و for در زبان PHP آشنا شدیم؛ حال در این آموزش قصد داریم تا به معرفی ساختار و کاربرد حلقه‌ٔ while بپردازیم. به طور کلی ساختار این حلقه به صورت زیر است:

while (condition) {
   //Code block to be executed
}

برخلاف حلقهٔ for که ساختار پیچده‌ای داشت، while را می‌توان به نوعی ساده‌ترین نوع حلقه‌ها در این زبان قلمداد کرد. در حقیقت، در ابتدای هر بار اجرای حلقه، Condition یا به عبارتی شرط در نظر گرفته شده چک می‌شود و مادامی که این شرط به اصطلاح True باشد، اجرای این اسکریپت ادامه خواهد یافت و به محض False شدن شرط، اجرای حلقه متوقف خواهد شد. اگر بخواهیم به شکلی بصری به این روند نگاه کنیم، خواهیم داشت:

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

حال ببینیم کاربرد حلقهٔ‌ while به چه شکل است. برای این منظور، در اسکریپتی که در ادامه مشاهده می‌کنید قصد داریم تا با استفاده از حلقهٔ while اعداد ۱ تا ۱۰ بشماریم:

$counter = 1;
while ($counter <= 10) {
    echo "I`ve counted to $counter<br>";
    $counter++;
}
echo "All done!";

ابتدا متغیری تحت عنوان counter$ با مقدار پیش‌فرض ۱ تعریف کرده‌ایم؛ سپس به عنوان شرط حلقهٔ while گفته‌ایم مادامی که مقدار این متغیر کوچک‌تر یا مساوی با ۱۰ بود، تکرار اسکریپت‌های نوشته‌شده داخل { } ادامه یابد. پس از چاپ کردن مقدار counter$ با استفاده از دستور echo، پیش از پایان یافتن هر بار اجرای کد، در خط چهارم یک واحد به مقدار این متغیر اضافه کرده‌ایم. به عنوان خروجی هم خواهیم داشت:

I`ve counted to 1
I`ve counted to 2
I`ve counted to 3
I`ve counted to 4
I`ve counted to 5
I`ve counted to 6
I`ve counted to 7
I`ve counted to 8
I`ve counted to 9
I`ve counted to 10
All done!

در واقع شرط قرار گرفته در این حلقه True است تا زمانی که مقدار متغیر counter$ برابر با ۱۱ شود که مسلماً در این صورت شرط False شده و از حلقه خارج خواهیم شد.

نحوهٔ استفاده از حلقهٔ do while در زبان PHP


do while ورژنی از همان حلقهٔ while است که در آموزش گذشته با آن آشنا شدیم با این تفاوت که شرط مرتبط با حلقه پس از اینکه حداقل یک بار بلوک کد اجرا شد، بررسی می‌گردد. به عبارت دیگر، در مواقعی کاربرد دارد که بخواهیم اسکریپتی را حداقل یک بار اجرا کرده سپس با چک کردن شرط، در مورد تکرار مجدد اسکریپت و یا خارج شدن از حلقه تصمیم بگیریم. ساختار کلی این حلقه عبارت است از:

do {
  // This code is run at least once
} while (condition)

// This code is run after the loop finishes

در واقع، مفسر PHP ابتدا کدهای قرار گرفته داخل { } را اجرا کرده سپس Condition یا شرط را مورد بررسی قرار می‌دهد؛‌ چنانچه این شرط برقرار بود، کدهای مد نظر مجدد اجرا می‌شوند و در غیر این صورت، اسکریپت متوقف خواهد شد. چنانچه بخواهیم این پروسه را به شکل بصری ترسیم کنیم، فلوچارت زیر را خواهیم داشت:

سناریوی فرضی سرویس بهداشتی برای درک بهتر کاربرد این حلقه
اگر بخواهیم کاربرد do while را با مثالی از دنیای واقعی مقایسه کنیم، می‌توان سناریویی فرضی را متصور شد که در آن قصد استفاده از سرویس بهداشتی عمومی را داریم!

do {
    lockTheDoor();
} while ($peeing);

فرض کنیم که در مکانی عمومی قصد استفاده از سرویس بهداشتی را داریم که در چنین موقعیتی، منطق حکم می‌کند پیشاز آنکه کار خود را شروع کنیم! از قفل بودن درب سرویس اطمینان حاصل کنیم. لذا همان‌طور که در کد فوق می‌بینیم، داخل بلوک { } ابتدا فانکشنی تحت عنوان ()lockTheDoor به معنی تحت‌الفظی «در را قفل کن» را فراخوانی کرده‌ایم (به عبارت دیگر، پیش از هر چیز چک می‌کنیم ببنیم که آیا درب قبل است یا خیر.) در ادامه، مادامی که شرط در نظر گرفته شده برای while برقرار باشد، در قفل خواهد ماند؛ یعنی مادامی که مشغول Pee (دستشویی کردن) باشید، درب دستشویی کماکان قفل خواهد ماند.

ساخت گیم حدس عدد با استفاده از do while
به منظور درک بهتر عملکرد این نوع از حلقه‌ها در زبان PHP، در ادامه حلقهٔ do while را در قالب یک گیم مورد استفاده قرار خواهیم داد:

$theNumber = rand(1, 10);
echo "The number is $theNumber<br>";
do {
    $myGuess = rand(1, 10);
    echo "I‍`m guessing: $myGuess</br>";
} while ($myGuess != $theNumber);
echo "I got it! It`s $myGuess!<br>";

ابتدا به تفسیر کدهای فوق پرداخته، سپس چند بار آن را تست می‌کنیم تا خروجی را مشاهده نماییم. ابتدا متغیری تحت عنوان theNumber$ تعریف کرده‌ایم که مقدار اولیه‌اش عددی تصادفی است که با استفاده از تابع به اصطلاح Built-in (از پیش تعریف شده) در زبان PHP تحت عنوان ()rand تعیین می‌گردد که این عدد تصادفی در بازهٔ ۱ تا ۱۰ انتخاب خواهد شد و سپس با استفاده از دستور echo این عدد را چاپ می‌کنیم.

حال می‌رسیم به کدهای قرار گرفته داخل { } که بدون اینکه ابتدا به ساکن شرط این حلقه چک شود و از True بودن آن اطمینان حاصل گردد، حداقل یک بار اجرا خواهد شد و آن هم چیزی نیست جز ساخت متغیری دیگر تحت عنوان myGuess$ که این متغیر هم دقیقاً همچون متغیر theNumber$ مقداردهی می‌شود؛ به عبارتی، یک عدد رَندوم (تصادفی) در بازهٔ ۱ تا ۱۰ برایش در نظر گرفته خواهد شد. در ادامه، استرینگی روی صفحه چاپ می‌کنیم با این مضمون که «عددی که حدس می‌زنم برابر است با …» و … را با مقدار متغیر myGuess$ جایگزین می‌کنیم.

در شرط قرار گرفته داخل پرانتزهای مرتبط با while گفته‌ایم اگر مقدار متغیرهای myGuess$ و theNumber$ با همنامساوی بود، اجرای اسکریپت‌ها ادامه یابد تا زمانی که هر دو عدد مساوی شوند که در این صورت از حلقه خارج شده و در نهایت با استفاده از دستور echo عددی که درست حدس زده بودیم را چاپ خواهیم کرد. حال یک بار این اسکریپت را در لوکال‌هاست اجرا می‌کنیم:

The number is 8
I‍`m guessing: 10
I‍`m guessing: 2
I‍`m guessing: 7
I‍`m guessing: 2
I‍`m guessing: 1
I‍`m guessing: 8
I got it! It`s 8!

اکنون برای بار دوم دست به اجرای کد می‌زنیم:

The number is 7
I‍`m guessing: 8
I‍`m guessing: 10
I‍`m guessing: 3
I‍`m guessing: 9
I‍`m guessing: 8
I‍`m guessing: 3
I‍`m guessing: 3
I‍`m guessing: 8
I‍`m guessing: 6
I‍`m guessing: 7
I got it! It`s 7!

حال برای سومین بار این اسکریپت را اجرا می‌کنیم:

The number is 10
I‍`m guessing: 10
I got it! It`s 10!

دو بار اولی که کد را اجرا کردیم، عددی که ابتدا حدس زده‌ بودیم درست نبود؛ لذا این حلقه آن‌قدر ادامه یافت تا به عدد درست دست پیدا کردیم اما در اجرای سوم، همان‌طور که ملاحظه می‌شود، عدد رَندوم انتخابی سیستم برابر با ۱۰ بود و این عدد در خروجی چاپ شد؛ سپس وارد بلوک { } شده و یک عدد تصادفی به متغیر myGuess$ اختصاص یافته که از قضا این عدد هم برابر با ۱۰ بود و در خروجی چاپ شد. حال می‌رسیم به شرط قرار گرفته داخل پرانتزهای مرتبط با while و از آنجا که هر دو متغیر myGuess$ و theNumber$ با یکدیگر مساوی هستند (به عبارتی شرط False است)، لذا از حلقه خارج شده و در نهایت استرینگ قرار گرفته مقابل دستور echo در خط هفتم اجرا می‌گردد.

درآمدی بر کاربردهای دستور break در حلقه‌ها در زبان PHP


خواه از foreach استفاده کنیم و خواه از دیگر انواع حلقه‌های PHP همچون for و while، گاهی نیاز خواهیم داشت تا بسته به منطق وب‌ اپلیکیشن‌مان، در روند اجرای حلقه‌ها دخالت نماییم که برای این منظور، می‌توان از دستورات break و continue استفاده کرد که در این آموزش تمرکز روی دستور break بوده و در آموزش بعد بیشتر با کاربردهای continue آشنا خواهید شد.

آشنایی با دستور break در زبان PHP
در مبحث آشنایی با دستور switch در زبان PHP، با کاربرد دستور break آشنا شدیم. در حقیقت، break به منظور خاتمه دادن به پروسهٔ اجرای یک حلقه می‌تواند مورد استفاده قرار گیرد:

همان‌طور که در تصویر فوق مشاهده می‌شود، در دو صورت کلی است که به نقطهٔ پایانی برنامه‌ می‌رسیم:

– چنانچه شرط اصطلاحاً False باشد.
– چنانچه دستور break در حلقه استفاده شده باشد.

برای درک بهتر کاربرد break در حلقه‌ها، سناریویی را در دنیای واقعی در نظر می‌گیریم بدین صورت که در وب اپلیکیشن خود این امکان را در اختیار کاربران قرار می‌دهیم که جهت لاگین کردن به سایت، سه بار تلاش کنند و چنانچه در فرصت‌های در نظر گرفته‌ شده و با استفاده از نام‌کاربری و رمزعبور صحیح موفق به لاگین کردن نشوند، به منظور رعایت مسائل امنیتی، تا چند دقیقه اجازه تلاش جهت ورود به سایت را نخواهند داشت. نکتهاین مکانیسمی است که اکثر سایت‌ها برای جلوگیری از فعالیت بات‌ها اِعمال می‌کنند.

حال چنانچه بخواهیم چنین چیزی را در وب اپلیکیشن خود پیاده کنیم، خواهیم داشت:

$tries = 0;
$username = 'admin';
$password = '123456';
$userData = ['username' => 'behzad', 'password' => '9f41a95cba557b2894771eed96e07a4ded82537f'];

for ($counter = 1 ; ; $counter = $counter + 1) {
    $tries++;
    echo "Please enter you username in here ... and your password in here ... (It`s your try No $counter)<br>";
    if ($tries == 3) {
        echo "You tries more than $tries times and you are blocked!";
        break;
    } else if ($username == $userData['username'] && $password == $userData['password']) {
        echo "After $tries try(ies), You are logged in successfully.";
        break;
    }
}

ابتدا به تفسیر برنامه‌ٔ فوق پرداخته سپس آن را اجرا می‌کنیم. همان‌طور که در خط اول ملاحظه می‌شود، متغیری ساخته‌ایم تحت عنوان tries$ با مقدار پیش‌فرض صفر که این وظیفه را در برنامه‌ٔ ما خواهد داشت تا تعداد دفعاتی که کاربر برای لاگین تلاش می‌کند را در خود ذخیره سازد. در ادامه نیز دو متغیر تحت عناوین username$ و password$ ایجاد کرده‌ایم به ترتیب با مقادیری همچون admin و 123456 و در نهایت هم آرایه‌ای تحت عنوان userData$ داریم که حاوی دو اندیس تحت عناوین username و password است که مقادیری دلخواه همچون چیزهایی که ملاحظه می‌کنید برایشان در نظر گرفته شده است.

برای نوشتن این برنامه، از حلقهٔ for استفاده کرده‌ایم اما این در حالی است که با هر ساختار دیگری می‌شد آن را نوشت (حتی اصولی‌تر) اما با توجه به اینکه قصد داریم تا آنچه تاکنون آموخته‌ایم را با یکدیگر ادغام نماییم، از این نوع حلقه استفاده شده به گونه‌ای که پارامتر دوم این حلقه (شرط) را حذف کرده‌ایم به طوری که اگر دستور break داخل { } اصلاً استفاده نشده باشد، این حلقه تا بی‌نهایت اجرا خواهد شد.

به عنوان پارامتر اول این حلقه،‌ متغیری تعریف کرده‌ایم تحت عنوان counter$ به معنی شمارنده که مقدار پیش‌فرض یک برایش در نظر گرفته شده که این متغیر قرار است تا به کاربر نشان دهد که دفعهٔ چندم است که برای ورود به سایت تلاش می‌کند. همان‌طور که پیش از این گفتیم، پارامتر دوم (شرط) حذف شده اما کماکان علامت ; مرتبط با آن سر جایش باقی است که در غیر این صورت با ارور مواجه خواهیم شد و در نهایت به پارامتر سوم (Step) می‌رسیم که در این بخش دستور داده‌ایم تا در هر بار اجرای حلقه، مقدار متغیر counter$ یک واحد افزایش یابد (این در حالی است که به جای این ساختار خیلی راحت‌تر می‌شد تا از ++counter$ استفاده کرد اما دلیل استفاده از این رویکرد فقط نشان دادن حالات مختلف کدنویسی است.)

اسکریپت داخل { } پیش از هر چیز با اصطلاحاً Increment یا افزایش یک واحد به متغیر tries$ شروع می‌شود چرا که می‌خواهیم در هر بار اجرا یک واحد به مقدار پیش‌فرض این متغیر که صفر است اضافه کنیم تا متوجه شویم کاربر چند بار برای ورود به سایت تلاش کرده است و چنانچه از حد مجاز (سه دفعه) تجاوز کرد، جلوی وی را بگیریم. سپس با استفاده از دستور echo اِسترینگی را چاپ می‌‌کنیم با این مضمون که نام‌کاربری و رمزعبور خود را وارد نمایید.

سپس از یک دستور شرطی if else if استفاده نموده‌ایم بدین صورت که شرط if گفته‌ایم که اگر مقدار متغیر tries$ برابر با ۳ بود، متنی در معرض دید کاربر قرار گیرد با این مضمون که «شما بیش از ۳ بار اقدام به ورود به سایت کرده‌اید و مسدود هستید!» و نکتهٔ بسیار مهم اینجا است که در این بلوک حتماً می‌بایست از دستور break استفاده نماییم تا از حلقه خارج شویم. در دستور شرطی دوم یا else if هم گفته‌ایم که اگر مقدار متغیرهای username$ و password$ برابر با مقادیر در نظر گرفته‌ شده برای اندیس‌های username و password در آرایهٔ userData$ بود، این بدان معنا است که نام‌کاربری و رمزعبور صحیح هستند و کاربر بایستی لاگین شود که برای همین منظور، اِسترینگی با معنای تحت‌الفظی «شما با موفقیت لاگین شدید.» در معرض دید کاربر قرار می‌دهیم اما مجدد نکتهٔ مهمی که در این بخش از کد وجود دارد الزام استفاده از دستور break است چرا که قصد داریم به محض اینکه دیتای ورودی صحیح بود، از حلقه خارج شویم. حال یک بار اسکریپت فوق را اجرا می‌کنیم:

Please enter you username in here ... and your password in here ... (It`s your try No 1)
Please enter you username in here ... and your password in here ... (It`s your try No 2)
Please enter you username in here ... and your password in here ... (It`s your try No 3)
You tries more than 3 times and you are blocked!

در تفسیر نحوهٔ عملکرد برنامه در مثال فوق، بایستی گفت که مقدار در نظر گرفته‌ شده برای اندیس‌های username و password با مقدار پیش‌فرض متغیرهای username$ و password$ یکسان نیستند؛ پس هرگز وارد بلوک else if نخواهیم شد بلکه در عوض اجرای اسکریپت‌های داخل { } ادامه می‌یابد و هر دفعه هم یک واحد به مقدار متغیر tries$ اضافه می‌گردد و این کار تا زمانی ادامه می‌یابد که این مقدار به عدد ۳ رسیده که در این صورت وارد بلوک if می‌شویم و اینجا است که به کاربر (یا ربات) هشدار داده می‌شود که بیش از حد مجاز برای ورود به سایت تلاش کرده، فلذا مسدود شده است و با استفاده از دستور break هم از این حلقه خارج می‌شویم. برای بار دوم اجرا، ابتدا اسکریپت فوق را به شکل زیر ریفکتور کرده سپس دست به اجرای آن می‌زنیم:

$tries = 0;
$username = 'admin';
$password = '123456';
$userData = ['username' => 'admin', 'password' => '123456'];

for ($counter = 1 ; ; $counter = $counter + 1) {
    $tries++;
    echo "Please enter you username in here ... and your password in here ... (It`s your try No $counter)<br>";
    if ($tries == 3) {
        echo "You tries more than $tries times and you are blocked!";
        break;
    } else if ($username == $userData['username'] && $password == $userData['password']) {
        echo "After $tries try(ies), You are logged in successfully.";
        break;
    }
}

به عنوان خروجی هم خواهیم داشت:

Please enter you username in here ... and your password in here ... (It`s your try No 1)
After 1 try(ies), You are logged in successfully.

در واقع، این بار حلقه فقط یک مرتبه اجرا شده، مقدار متغیر tries$ از صفر به یک تغییر یافته و مستقیماً وارد بلوک else if شده‌ایم چرا که مقادیر پیش‌فرض اندیس‌های username و password با مقادیر پیش‌فرض متغیرهای username$ و password$ یکسانند اما مجدد بایستی گفت که نکتهٔ مهم در اینجا، استفاده از دستور break داخل بلوک else if است که در غیر این صورت، برنامه‌ به درستی کار نخواهد کرد. به عنوان مثال داریم:

if ($tries == 3) {
    echo "You tries more than $tries times and you are blocked!";
    break;
} else if ($username == $userData['username'] && $password == $userData['password']) {
    echo "After $tries try(ies), You are logged in successfully.";
    // break;
}

همان‌طور که ملاحظه می‌شود، دستور break قرار گرفته داخل بلوک else if را کامنت کرده‌ایم. حال یک بار دیگر برنامه را اجرا می‌کنیم:

Please enter you username in here ... and your password in here ... (It`s your try No 1)
After 1 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 2)
After 2 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 3)
You tries more than 3 times and you are blocked!

می‌بینیم علیرغم اینکه نام‌کاربری و رمزعبور صحیح هستند، اما مسدود شدیم و دلیل این مسئله هم آن است که هیچ منطقی در برنامه وجود ندارد تا پس از درست بودن دیتای کاربر، وی را از حلقه خارج سازد و این کار آن‌قدر ادامه می‌یابد تا در نهایت تعداد دفعات مجاز تلاش برای ورود به سایت بیش از ۳ بار شده و وارد بلوک if شویم. حال اگر دستور break داخل if را هم به صورت زیر کامنت کنیم، نتیجه کاملاً‌ مشخص است که داخل یک حلقهٔ به اصطلاح Infinite (بی‌پایان) خواهیم افتاد:

if ($tries == 3) {
    echo "You tries more than $tries times and you are blocked!";
    // break;
} else if ($username == $userData['username'] && $password == $userData['password']) {
    echo "After $tries try(ies), You are logged in successfully.";
    // break;
}

به عنوان خروجی داریم:

Please enter you username in here ... and your password in here ... (It`s your try No 1)
After 1 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 2)
After 2 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 3)
You tries more than 3 times and you are blocked!Please enter you username in here ... and your password in here ... (It`s your try No 4)
After 4 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 5)
After 5 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 6)
After 6 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 7)
After 7 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 8)
After 8 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 9)
After 9 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 10)
After 10 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 11)
After 11 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 12)
After 12 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 13)
After 13 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 14)
After 14 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 15)
After 15 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 16)
After 16 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 17)
After 17 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 18)
After 18 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 19)
After 19 try(ies), You are logged in successfully.Please enter you username in here ... and your password in here ... (It`s your try No 20)
.
.
.

این حلقه تا بی‌نهایت ادامه خواهد داشت تا ما اقدام به متوقف کردن برنامه به صورت دستی کنیم!

درآمدی بر کاربردهای دستور continue در حلقه‌ها در زبان PHP


کلیدواژهٔ continue در زبان PHP این کاربرد را دارا است تا بسته به شرطی که در نظر گرفته‌ایم، یک Iteration (چرخش) حلقه را متوقف سازد اما این در حالی است که از کل حلقه بیرون نخواهیم رفت:

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

الگوریتم فرضی گوگل برای تحریم کاربران ایرانی
نیاز به توضیح نیست که دولوپرهای ایرانی به بسیاری از سرویس‌های آمریکایی همچون بخش‌هایی از گوگل مثل developers.google.com دسترسی ندارند. حال فرض کنیم گوگل برای محدود کردن ایران و دیگر کشورهای تحریمی مثل کرهٔ شمالی، سوریه و  غیره، از الگوریتم زیر استفاده کرده باشد:

$countries = ['England', 'Iran', 'North Korea', 'Russia', 'Syria', 'Cuba', 'Canada'];
$url = 'https://developers.google.com/';
foreach ($countries as $country) {
    if ($country == 'Iran' || $country == 'North Korea' || $country == 'Syria' || $country == 'Cuba') {
        continue;
    }
    echo "$country is allowed to access $url<br>";
}

در خط اول آرایه‌ای تحت عنوان countries$ داریم که حاوی نام یک سری کشور همچون انگلستان، ایران، روسیه، کانادا و کشورهای دوست و همسایه! کرهٔ شمالی، سوریه و کوبا است. سپس آرایه‌ٔ دیگری تحت‌عنوان url$ ساخته‌ایم که مقدار آن را برابر با لینک سایت گوگل دولوپرز قرار داده‌ایم.

در ادامه، از یک حلقهٔ foreach استفاده نموده‌ایم بدین صورت که داخل این حلقه‌ شرطی گذاشته‌ایم مبنی بر این که اگر نام کشوری یکی از گزینه‌های Syria ،North Koria ،Iran و Cuba بود (علامت || به معنی یا است)، با استفاده از دستور continue این گزینه از آرایهٔ ما نادیده گرفته شده و مفسر PHP مجدد به ابتدای حلقه رفته و موارد دیگر را بررسی کند. در نهایت هم با استفاده از دستور echo نام کشورهایی که مجاز به استفاده از این سرویس گوگل هستند را چاپ می‌‌کنیم به طوری که به عنوان خروجی اسکریپت فوق داریم:

England is allowed to access https://developers.google.com/
Russia is allowed to access https://developers.google.com/
Canada is allowed to access https://developers.google.com/

حال برای این که عمیق‌تر با نحوهٔ کار با آرایه‌ها در زبان PHP آشنا شویم، کد فوق را به شکل زیر تکمیل می‌کنیم:

$countries = ['England', 'Iran', 'North Korea', 'Russia', 'Syria', 'Cuba', 'Canada'];
$url = 'https://developers.google.com/';
$theCountriesUnderSanction;
foreach ($countries as $country) {
    if ($country == 'Iran' || $country == 'North Korea' || $country == 'Syria' || $country == 'Cuba') {
        $theCountriesUnderSanction[] = $country;
        continue;
    }
    echo "$country is allowed to access $url<br>";
}
if (count($theCountriesUnderSanction) > 0) {
    echo '<br>';
    foreach ($theCountriesUnderSanction as $country) {
        echo "$url is limited for $country<br>";
    }
}

ابتدا اسکریپت جدید را اجرا کرده و خروجی را مشاهده می‌کنیم، سپس به تفسیر کدها خواهیم پرداخت:

England is allowed to access https://developers.google.com/
Russia is allowed to access https://developers.google.com/
Canada is allowed to access https://developers.google.com/

https://developers.google.com/ is limited for Iran
https://developers.google.com/ is limited for North Korea
https://developers.google.com/ is limited for Syria
https://developers.google.com/ is limited for Cuba

در تفسیر کدهای جدید بایستی گفت که پیش از هر چیز یک متغیر جدید تحت عنوان theCountriesUnderSanction$ (کشورهای تحریمی) ساخته‌ایم که هیچ مقدار پیش‌فرضی برایش در نظر گرفته نشده و این در حالی است که در خط ششم در foreach اول قصد داریم آن را پر نماییم بدین صورت که جایی که کشورهای تحریمی با استفاده از یک دستور شرطی مشخص شده‌اند، مقدار متغیر country$ را در هر بار چرخش حلقه، به عنوان یکی از کلیدهای متغیر یا بهتر بگوییم آرایهٔ theCountriesUnderSanction$ ریخته‌ایم. نکتهچیزی که در این رابطه بسیار حائز اهمیت است این که حتماً بایستی پس از theCountriesUnderSanction$ علائم [ ] را قرار داد که در غیر این صورت فقط و فقط همواره آخرین مقدار country$ در آن ذخیره خواهد شد. به عبارتی، علائم [ ] متغیر theCountriesUnderSanction$ را به یک آرایه تبدیل کرده‌اند.

در ادامه و در خط یازدهم از یک دستور شرطی استفاده کرده‌ایم بدین منظور که چک کنیم ببینیم آیا هیچ دیتایی داخل متغیر theCountriesUnderSanction$ ذخیره شده‌ است یا خیر که اگر شرط برقرار بود، کدهای داخل { } اجرا خواهند شد (در حقیقت، تابع از پیش تعریف شدهٔ ()count تعداد خانه‌های یک آرایه را بازمی‌گرداند و در این شرط گفته‌ایم که اگر این تعداد بزرگ‌تر از صفر بود، یا به عبارتی محتوایی داخل این آرایه قرار داشت ولو یک اِلِمان، دستوارتی که در ادامه آمده‌اند اجرا شوند.) در ادامه، مجدد از یک حلقهٔ foreach استفاده نمود و به عنوان ورودی‌اش آرایهٔ theCountriesUnderSanction$ را به این لوپ پاس داده‌ایم تا برایمان لیست کشورهای تحریم‌شده را چاپ نماید.

 ادامهٔ دوره در دست تالیف است.

مطالب مرتبط

پاسخی بگذارید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *