استخدام المصفوفات  2 في PHP


استخدام المصفوفات

الجزء الثاني


خامساً : فرز المصفوفات:

عندما تكون البيانات المخزنة في المصفوفات مرتبطة ببعضها البعض يكون فرزها سهل.

·         استخدام التابع  sort()

يقوم هذا التابع بترتيب عناصر المصفوفة التي تمرر له كوسيط ويعطي النتيجة في نفس المصفوفة على الشكل التالي:
$products = array ( ‘Tires’, ‘Oil’, ‘Spark Plugs’ );
sort($products);

في هذا المثال يتم ترتيب عناصر المصفوفة $products ترتيباً أبجدياً ، وبالتالي ستظهر عناصر المصفوفة بعد الترتيب عل الشكل :    Oil , Spark Plugs , Tires

يمكننا أيضاً فرز عناصر المصفوفة حسب الترتيب العددي إذا كان لدينا مصفوفة تحتوي على أرقام على الشكل التالي:
$prices = array ( 100, 10, 4 );
sort($prices);

ستظهر عناصر المصفوفة $prices بعد الترتيب على  الشكل: 4 ، 10 ، 100.
كما أنه يجب الانتباه إلى أن التابع  sort()  حساس لحالة الأحرف فجميع الحروف الكبيرة تأتي قبل الحروف الصغيرة.
في الحقيقة يملك التابع sort() وسيط آخر اختياري لتحديد نوع الترتيب ، وهذا الوسيط يمكن أن يكون أحد الثوابت التالية:

SORT_REGULAR (الافتراضي)  ,  SORT_NUMERIC , SORT_STRING


نحتاج إلى تحديد نوع الفرز عند مقارنة السلاسل المحرفية التي تحتوي على أرقام فمثلاً : 2 و 12  إذا اعتبرناهما أعداد فإن 2 أقل من 12 لكن إذا اعتبرناهما محارف فإن 12 أقل من 2 .

      استخدام التوابع  ,  asort() ksort()   لفرز المصفوفات:

إذا كنا نستخدم مصفوفات تحوي مفاتيح وصفية لتخزين العناصر وأسعارها ، فستحتاج إلى استخدم أنواعًا مختلفة من توابع الفرز للحفاظ على المفاتيح والقيم معًا عند فرزها.
في التعليمات البرمجية التالية سنقوم بإنشاء مصفوفة تحتوي على المنتجات الثلاثة وما يرتبط بها من الأسعار ثم سنقوم بفرز المصفوفة تصاعدياً حسب الأسعار:
$prices = array ( ‘Tires’=>100, ‘Oil’=>10, ‘Spark Plugs’=>4 );
asort($prices);

هنا يقوم التابع asort()  بترتيب المصفوفة وفقًا لقيمة كل عنصر، القيم هنا هي الأسعار ، والمفاتيح هي الأوصاف النصية.

 إذا أردنا الترتيب حسب الوصف وليس حسب السعر نحتاج إلى استخدام التابع  ksort() ، الذي يفرز المصفوفة حسب المفتاح وليس حسب القيمة على الشكل التالي:

$prices = array ( ‘Tires’=>100, ‘Oil’=>10, ‘Spark Plugs’=>4 );
             ksort($prices);
ينتج عن هذه التعليمات البرمجية الترتيب التالي: Oil , Spark Plugs , Tires  .

·         الفرز العكسي للمصفوفات:

تقوم توابع الفرز الثلاثة المختلفة:  sort() , asort() , ksort()  بفرز المصفوفة في ترتيب تصاعدي ولكل تابع يوجد تابع مطابق عكسي  لفرز المصفوفة في ترتيب تنازلي ، هذه التوابع العكسية هي  rsort() , arsort() , krsort()  حيث يمكننا استخدام توابع الفرز العكسي بنفس الطريقة التي تستخدم بها توابع الفرز التصاعدي.
وبالتالي يقوم التابع rsort()  بفرز عناصر مصفوفة مفهرسة رقمياً أحادية البعد وفق ترتيب تنازلي و يقوم التابع arsort()  بفرز مصفوفة أحادية البعد وفق ترتيب تنازلي باستخدام قيمة كل عنصر ويقوم التابع krsort()   بفرز مصفوفة أحادية البعد وفق ترتيب تنازلي باستخدام مفتاح كل عنصر.

·         فرز المصفوفات متعددة الأبعاد:

فرز المصفوفات متعددة الأبعاد هو أكثر تعقيداً من فرز المصفوفات أحادية البعد ، فبالنسبة للمصفوفات الأحادية البعد يكون كل عنصر عبارة عن قيمة وبالتالي لغة PHP تعرف كيف تقارن رقمين أو سلسلتين نصيتين ، أما في المصفوفة متعدد الأبعاد يكون كل عنصر عبارة عن مصفوفة وبالتالي لغة PHP  لا تعرف كيف تقان بين مصفوفتين، لذلك نحتاج هنا إلى إنشاء طريقة برجية لمقارنتها.
كما أنه يجب الانتباه إلى أنه في معظم الأحيان يكون ترتيب الكلمات أو الأرقام واضحًا إلى حد ما ، ولكنه يصبح معقداً بالنسبة للأغراض objects.

·         الترتيب المعرف من قبل المستخدم:

فيما يلي سنكتب كود لتعريف مصفوفة ثنائية البعد ، هذه المصفوفة تم ذكرها سابقاً وهي تخزن المنتجات الثلاثة في شركة بوب و تحتوي على رمز ووصف وسعر لكل منتج:
$products = array ( array( ‘TIR’, ‘Tires’, 100 ),
                            array( ‘OIL’, ‘Oil’, 10 ),
                            array( ‘SPK’, ‘Spark Plugs’, 4 ) );

إذا أردنا فرز هذه المصفوفة ، فبإمكاننا الفرز وفق طريقتين : إما فرز المنتجات في الترتيب الأبجدي باستخدام الوصف أو فرز المنتجات في الترتيب الرقمي باستخدام السعر.

حتى نقو بذلك علينا استخدام التابع usort()  وإخبار لغة  PHP عن كيفية المقارنة بين العناصر، وبالتالي يجب أن نكتب الكود البرمجي الخاص بنا ، لذا سنكتب كود للمقارنة بين عناصر هذه المصفوفة باستخدام الوصف على الشكل التالي:

function compare ($x, $y)  
{
    if ($x[1] == $y[1])
     {
        return 0;
     }
   else if ($x[1] < $y[1])
     {
        return -1;
     }
  else  
    {
       return 1;
    }
}

usort($products, 'compare');

قمنا هنا بتعريف تابع خاص بنا يسمى  compare  هذا التابع له وسيطين هما   $x, $y  وهما يمثلان مصفوفتين من المصفوفة الرئيسية أي أن كل منهما يمثل منتجاً من المنتجات ، ويقوم هذا التابع بالمقارنة بين المنتجين من خلال الوصف وليس القيمة لذا نكتب $x[1] ,  $y[1]  وليس $x[0] , $y[0]    لأن الوصف هو العنصر الثاني من كل مصفوفة.
وبالنهاية يعيد لنا التابع قيمة معينة حسب نتيجة المقارنة (0 , 1 , -1)  من خلال الكلمة المفتاحية return هذه القيمة المرجعة من التابع ستستخدم من قبل التابع usort() وهو تابع موجود مسبقاً ضمن مكتبة PHP وهو يأخذ وسيطين هما المصفوفة التي نريد ترتيبها ونتيجة التابع compare ، وبالنهاية يعطينا هذا التابع  مصفوفة المنتجات مرتبة تصاعدياً حسب الوصف.

في حال أردنا فرز المصفوفة بترتيب أخر (حسب السعر مثلاً) يمكننا ببساطة إعادة كتابة التابع compare على الشكل التالي: 

function compare($x, $y)
 {
   if ($x[2] == $y[2])
   {
     return 0;
   }
 else if ($x[2] < $y[2])
  {
   return -1;
  }
else
  {
    return 1;
  }
}
وهنا عندما يتم استدعاء التابع  usort($products, 'compare') يتم وضع مصفوفة المنتجات بترتيب تصاعدي حسب السعر.
حرف الـ u الموجود في اسم التابعusort()   يعني user ، أي أن هذا التابع يتطلب تعريف وبرمجة تابع مقارنة من قبل المستخدم ، وهناك أيضاً التوابع uasort() , uksort ()   وهي إصدارات من التوابع assort() , ksort()   وهي تتطلب أيضاً توابع مقارنة معرفة من قبل المستخدم.
على غرار  asort() يجب استخدام  uasort()  عند فرز المصفوفات غير المفهرسة رقمياً حسب القيمة حيث نستخدم asort()  إذا كانت عناصر المصفوفة عبارة عن أرقام أو نص بسيط ، أما إذا كانت عناصر المصفوفة عبارة عن مصفوفات أو أغراض نستخدم التابع  uasort()  .

على غرار  ksort() يجب استخدام  uksort()  عند فرز المصفوفات غير المفهرسة رقمياً حسب المفتاح حيث نستخدم ksort()  إذا كانت مفاتيح المصفوفة عبارة عن أرقام أو نص بسيط ، أما إذا كانت مفاتيح المصفوفة عبارة عن مصفوفات أو أغراض نستخدم التابع  uksort()  .

·         الترتيب العكسي المعرف من قبل المستخدم:

تملك التوابع الجاهزة  sort()  و asort()  و ksort()  توابع عكسية مطابقة لها ، بينما لا تملك التوابع المعرفة من قبل المستخدم توابع عكسية مطابقة لها ، لذا يتوجب على المستخدم كتابة توابع عكسية لتوابع المقارنة السابقة المعرفة من قبل المستخدم وذلك من أجل فرز عناصر مصفوفة متعددة الأبعاد وفق ترتيب عكسي، وذلك على الشكل التالي:

function reverse_compare($x, $y)
{
  if ($x[2] == $y[2])
   {
          return 0;
   }
 else if ($x[2] < $y[2])
   {
     return 1;
   }
 else
  {
    return -1;
  }
}

والآن سيؤدي استدعاء التابع usort($products, ‘reverse_compare’)   إلى ترتيب عناصر مصفوفة المنتجات وفق تسلسل تنازلي حسب السعر.

·         إعادة ترتيب المصفوفات:

قد نحتاج في بعض التطبيقات إلى ترتيب المصفوفات بطرق أخرى ، لذلك يوجد بعض التوابع الجاهزة في PHP  مثل shuffle() الذي يقوم بترتيب عناصر المصفوفة بشكل عشوائي ، والتابع array_reverse()
الذي يعطي نسخة من المصفوفة نفسها لكن بترتيب معاكس.

·         استخدام التابع shuffle() :
لنفرض أنه في مثال شركة بوب نريد أن نعرض عددًا صغيرًا من المنتجات على الصفحة الأولى من الموقع ، حيث يوجد عدد كبير من المنتجات ولكن نريد فقط ثلاثة منتجات نختارها عشوائياً لتظهر على الصفحة الرئيسية للموقع، وحتى لا يشعر الزائرون بالملل ، نريد أن تكون هذه المنتجات الثلاثة المختارة مختلفة لكل زيارة للموقع.
 يمكننا بسهولة تحقيق ذلك من خلال:
-       وضع صور جميع المنتجات ضمن مصفوفة.
-       تطبيق التابع shuffle()  على هذه المصفوفة حيث يقوم هذا التابع بترتيبها بشكل عشوائي.
-       عرض الصور الثلاثة الأولى من المصفوفة الناتجة عن الترتيب السابق.

وبالتالي سيكون الكود على الشكل التالي:
<?php
     $pictures = array ('tire.jpg', 'oil.jpg', 'spark_plug.jpg', 'door.jpg',
                               
 'steering_wheel.jpg','thermostat.jpg',
                                
 'wiper_blade.jpg','gasket.jpg', 'brake_pad.jpg');
     shuffle($pictures);
?>
<html>
<head>
<title>Bob's Auto Parts</title>
</head>
<body>
 <h1>Bob's Auto Parts</h1>
<div align="center">
<table width = 100%>
 <tr>
 <?php
        for ($i = 0; $i < 3; $i++)
          {
echo "<td align=\"center\"><img src=\"";
echo $pictures[$i];
echo "\"/></td>";
           }
?>
</tr>
</table>
</div>
</body>
·         استخدام التابع array_reverse() :
يأخذ هذا التابع مصفوفة ما كوسيط له ويقوم بإنشاء مصفوفة جديدة بنفس محتويات هذه المصفوفة لكن برتيب عكسي.
 مثلاً إذا كنا نريد إنشاء مصفوفة تحوي على العد التنازلي من 10 إلى 1 يوجد لدينا العديد من الطرق:
الطريق الأولى:

استخدام حلقة for لإنشاء مصفوفة تحوي على الأرقام من 10 إلى 1 على الشكل التالي:

$numbers = array();
for($i=10; $i>0; $i--)
  {
      array_push($numbers, $i);
 }
حيث قمنا هنا بتعيين قيمة البداية وهي 10 أي أعلى قيمة نريدها وفي كل دخول إلى الحلقة نقلل هذه القيمة بمقدار 1 من خلال العملية  (--)  إلى أن نصل إلى أدنى قيمة وهي 1 حسب الشرط الموجود في عبارة الـ for وهو $i>0.
نلاحظ أننا استخدمنا هنا مصفوفة فارغة وفي كل دخول إلى الحلقة نضيف عنصر إلى نهاية هذه المصفوفة من خلال التابع array_push() الذي يوجد له تابع معاكس هو array_pop()  حيث يقوم هذا التابع بإزالة عنصر واحد من نهاية المصفوفة.

الطريقة الثانية:
إنشاء مصفوفة تحوي على الأرقام من 1 إلى 10 وفق تسلسل تصاعدي من خلال التابع range()  ومن ثم استخدام التوابع array_reverse()  أو rsort()  من أجل الحصول على الترتيب التنازلي على الشكل التالي:

$numbers = range(1,10);
                 $numbers = array_reverse($numbers);

يجب أن نلاحظ أن التابع  array_reverse()  يقوم بإرجاع نسخة معدلة من المصفوفة ، أي أن التعديل يتم فوراً على نفس المصفوفة ، وبالتالي فإن النسخة الأصلية من المصفوفة لم تعد موجودة هنا.
الطريقة الثالثة:

إذا كانت المصفوفة مجرد مجموعة من الأعداد الصحيحة ، يمكن أنشاءها بترتيب عكسي فوراً من خلال التابع range()  لكن مع وجود وسيط اختياري ثالث يحدد الخطوة بين الأعداد على الشكل التالي:

$numbers = range(10, 1, -1);

سادساً : تحميل المصفوفات من الملفات:

بفرض لدينا ملف يحوي طلبات الزبائن ، وكل سطر من هذا الملف له الشكل التالي:
15:42, 20th April 4 tires 1 oil 6 spark plugs $434.00 22 Short St, Smalltown
ونريد معالجة هذه الطلبات من خلال تحميلها إلى مصفوفة ، لذا سنكتب البرنامج الذي يقوم بتحميل الملف إلى مصفوفة على الشكل التالي:

<?php
//create short variable name
$DOCUMENT_ROOT = $_SERVER['DOCUMENT_ROOT'];
$orders= file("$DOCUMENT_ROOT/../orders/orders.txt");
$number_of_orders = count($orders);
if ($number_of_orders == 0)
  {
echo "<p><strong>No orders pending.
Please try again later.</strong></p>";
  }
for ($i=0; $i<$number_of_orders; $i++)
  {
       echo $orders[$i]."<br />";
  }
يستخدم هذا البرنامج التابع file() الذي يحمل الملف بأكمله في مصفوفة بحيث يصبح كل سطر في الملف هو عنصر واحد من المصفوفة ، كما يستخدم هذا البرنامج التابع count() لمعرفة عدد العناصر الموجودة في المصفوفة.
يمكننا أيضاً معالجة الملف بطريقة أخرى من خلال تحميل كل قسم من أقسام الطلب إلى عنصر منفصل في المصفوفة وذلك من أجل معالجة هذا القسم بشكل منفصل أو لتنسيقه بطريقة أكثر جاذبية ، على الشكل التالي:
<?php
//create short variable name
$DOCUMENT_ROOT = $_SERVER['DOCUMENT_ROOT'];
?>
<html>
<head>
<title>Bob's Auto Parts - Customer Orders</title>
</head>
<body>
<h1>Bob's Auto Parts</h1>
<h2>Customer Orders</h2>
<?php
//Read in the entire file.
//Each order becomes an element in the array
$orders= file("$DOCUMENT_ROOT/../orders/orders.txt");
// count the number of orders in the array
$number_of_orders = count($orders);
if ($number_of_orders == 0)
  {
echo "<p><strong>No orders pending.
Please try again later.</strong></p>";
  }
echo "<table border=\"1\">\n";
echo "<tr><th bgcolor=\"#CCCCFF\">Order Date</th>
<th bgcolor=\"#CCCCFF\">Tires</th>
<th bgcolor=\"#CCCCFF\">Oil</th>
<th bgcolor=\"#CCCCFF\">Spark Plugs</th>
<th bgcolor=\"#CCCCFF\">Total</th>
<th bgcolor=\"#CCCCFF\">Address</th>
<tr>";
for ($i=0; $i<$number_of_orders; $i++)
  {
//split up each line
$line = explode("\t", $orders[$i]);
// keep only the number of items ordered
$line[1] = intval($line[1]);
$line[2] = intval($line[2]);
$line[3] = intval($line[3]);
// output each order
echo "<tr>
<td>".$line[0]."</td>
<td align=\"right\">".$line[1]."</td>
<td align=\"right\">".$line[2]."</td>
<td align=\"right\">".$line[3]."</td>
<td align=\"right\">".$line[4]."</td>
<td>".$line[5]."</td>
</tr>";
 }
echo "</table>";
?>
</body>

يستخدم هذا البرنامج التابع file() الذي يحمل الملف بأكمله في مصفوفة بحيث يصبح كل سطر في الملف هو عنصر واحد من المصفوفة كما في البرنامج السابق ، لكن الاختلاف هنا هو أن هذا البرنامج يستخدم التابع explode() الذي يقوم بتقسيم كل سطر عند مفتاح الجدولة ( \t ) وبالتالي يمكننا تطبيق بعض المعالجة والتنسيق على هذه العناصر المقسمة قبل الطباعة.

وسيكون الناتج من هذا البرنامج على الشكل التالي: 





إن الشكل العام للتابع  explode()  هو:
array explode (string separator ,  string string ,  [int limit])

حيث الوسيط الثاني هو المصفوفة التي نريد تقسيمها ، أما الوسيط الأول هو المفتاح الذي يتم عنده التقسيم وهو في برنامجنا هنا المفتاح  \t  ، فعلى سبيل المثال إذا طبقنا التابع explode(“\t” ,  $orders[$i]) على السلسلة التالية:
"20:43, 31st March 2008\t0 tires\t1 oil\t4 spark plugs\t$26.00\t127 Acacia St,
Springfield

سيكون ناتج التقسيم هو الأجزاء التالي:

“20:43, 31st March 2008”  ,  “0 tires”  ,  “1 oil”  ,   “4 spark plugs”  ,   “$26.00”  ,  “127 Acacia St, Springfield”.

كما يوجد للتابع explode()  وسيط ثالث اختياري يستخدم لتحديد الطول الأقصى للأجزاء المرجعة من التابع.
يقوم هذا البرنامج بإظهار طلبات الزبائن على شكل جدول كل سطر فيه يحوي عدد القطع المطلوبة من كل منتج وتاريخ الطلب والسعر الإجمالي للطلب ، حيث يتم استخراج هذه الأرقام من خلال التابع intval()  الذي يحول السلسلة إلى عدد صحيح وهذا التحويل ذكي إلى حد ما لأنه يتجاهل الأجزاء التي لا يمكن تحويلها إلى عدد صحيح.

سابعاً : التوابع functions   التي تتعلق بالمصفوفات:


·         توابع التنقل داخل المصفوفة:

each() , current() , reset() , end() , next() , pos() , prev()
يوجد لكل مصفوفة مؤشر داخلي يشير إلى عناصر المصفوفة ، فعند إنشاء مصفوفة جديدة يتم تهيئة هذا المؤشر بحيث يشير إلى العنصر الأول من المصفوفة ، وبالتالي فإن استدعاء التابع current($array_name)  يعطينا العنصر الأول بالمصفوفة ، بينما استدعاء التوابع next()  و  each()
يجعل المؤشر يمشي خطوة واحدة إلى الأمام لكن يوجد فرق بين هذين التابعين ، فالتابع each() يعطينا العنصر الحالي قبل تقدم المؤشر أما التابع next()  يعطينا العنصر الحالي بعد تقدم المؤشر.
التابع  reset() يعيد مؤشر إلى العنصر الأول في المصفوفة بينما التابع end() يعيد مؤشر إلى نهاية المصفوفة.
إذا أردنا التنقل ضمن المصفوفة ولكن بشكل عكسي نحتاج إلى التابعين  end()  و  prev()  ، فالتابع prev() هو عكس التابع next() حيث يجعل المؤشر يمشي خطوة إلى الوراء ثم يعطينا العنصر الحالي الجديد بعد تحرك المؤشر.
الكود التالي يعرض لنا عناصر المصفوفة بترتيب عكسي:
$value = end ($array);
while ($value)
{
echo “$value<br />”;
$value = prev($array);
}

·         تطبيق تابع ما على كل عنصر في المصفوفة:


-          استخدام التابع array_walk() :
في بعض الأحيان قد نحتاج إلى إجراء التعديل نفسه على كل عناصر المصفوفة ، نستطيع ذلك من خلال التابع array_walk()  الذي له الشكل التالي:
bool array_walk ( array arr , string func , [mixed userdata] )
هذا التابع يتطلب تعريف تابع من قبل المستخدم ليقوم بتطبيقه على عناصر المصفوفة ، حيث نلاحظ أن الوسيط الأول arr  هو المصفوفة المراد معالجتها ، والوسيط الثاني func هو اسم التابع المعرف من قبل المستخدم والذي سيتم تطبيقه على عناصر المصفوفة ، والوسيط الثالث userdata اختياري وفي حال استخدامه سيتم تمريره كوسيط إلى التابع func  وسنرى ذلك لاحقاً.
قد يكون التابع المعرف من قبل المستخدم هو فقط لعرض عناصر المصفوفة وفق تنسيق محدد كما في المثال التالي:
function my_print($value)
{
   echo “$value<br />”;
}
array_walk($array, ‘my_print’);

في هذا المثال نعرض كل عنصر من المصفوفة في سطر جديد عن طريق التابع  my_print()  المعرف من قبل المستخدم.
بالنسبة للتابع المعرف من قبل المستخدم غالباً ما نحتاج فقط إلى قيمة عناصر المصفوفة ولا علاقة لنا بمفاتيح المصفوفة ، لكن في بعض الحالات نحتاج إلى المفتاح والقيمة لكل عنصر بالإضافة إلى قيمة معينة نقوم بتمريرها إلى التابع.
للحصول على مثال أكثر تعقيدًا ولنبين استخدام الوسيط الاختياري userdata يمكننا كتابة تابع يقوم بتعديل القيم في المصفوفة ويتطلب وسيط ما يتم تمريره إلى التابع على الشكل التالي:

function my_multiply (&$value, $key, $factor)
{
            $value *= $factor;
}
array_walk (&$array , ‘my_multiply’ , 3) ;

يقوم هنا التابع my_multiply()  بمضاعفة كل عنصر في المصفوفة بواسطة العملية * ، لذا نحن هنا بحاجة إلى الوسيط الثالث الاختياري في التابع array_walk()  من أجل تمريره كوسيط إلى التابع my_multiply()  واستخدامه في عملية المضاعفة.
يمكن تجاهل الوسيط الثاني في التابع my_multiply وهو المفتاح لأنه لا يتم استخدامه داخل التابع  كما يجب الانتباه إلى الطريقة التي يتم بها تمرير الوسيط الأول وهو المصفوفة ، حيث يتم وضع العلامة (&) قبل اسم المتغير في تعريف التابع  my_multiply()   وهذا يعني أنه سيتم تمرير المصفوفة كمؤشر وليس كقيمة وهذا يسمح للتابع my_multiply() بإجراء تغييرات على هذه المصفوفة.


·         تحديد عدد العناصر في المصفوفة باستخدام count() , sizeof() , array_count _value() :



قمنا سابقاً باستخدام التابع  count() لحساب عدد العناصر في مصفوفة الطلبات ، ويوجد أيضاً التابع sizeof() وهو شبيه جداً بالتابع count() ويستخدم لنفس الغرض ، حيث يقوم كل منهما بإرجاع عدد العناصر في المصفوفة التي يتم تمريرها إليهما ، وفي حال كانت المصفوفة فارغة أو لم يتم تعيينها يقوم كل من التابعين بإرجاع القيمة صفر.
بينما التابع array_count_values​​() هو تابع أكثر تعقيدًا حيث يتم استخدامه على الشكل  array_count_values​​($array)  ويقوم بحساب عدد مرات الظهور لكل قيمة مختلفة في المصفوفة $array  ويقوم بإرجاع مصفوفة مفاتيحها هي القيم المختلفة التي تم إيجادها في $array وقيمها هي عدد مرات ظهور هذه المفاتيح ، أي كل مفتاح له قيمة تخبرنا بعدد مرات ظهور هذا المفتاح في المصفوفة $array .
مثال على ذلك:
$array = array (4, 5, 1, 2, 3, 1, 2, 1);
$ac = array_count_values ($array);

وبالتالي المصفوفة $ac  ستكون على الشكل التالي:
Key          Value
 4                 1
 5                 1
 1                 3
 2                 2
 3                 1


تشير هذه النتيجة إلى أن الأعداد  4 و 5 و 3 ظهرت مرة واحدة في المصفوفة $array ، وظهر العدد 1 ثلاث مرات ، والعدد 2 ظهر مرتين.

·         تحويل المصفوفة إلى متغيرات عددية باستخدام  : extract()

إذا كان لدينا مصفوفة غير مفهرسة رقمياً مع أزواج من القيم والمفاتيح فيمكننا تحويلها إلى مجموعة من المتغيرات العددية باستخدام التابع extract() الذي له الشكل العام التالي:

Extract (array var_array , [ int extract_type] , [ string prefix] ) ;

الهدف من استخدام التابع  extract() هو أخذ مصفوفة وإنشاء متغيرات عددية من هذه المصفوفة حيث تكون أسماء هذه المتغيرات هي أسماء المفاتيح في المصفوفة وقيم هذه المتغيرات هي القيم المقابلة لهذه المفاتيح في المصفوفة.
مثال على ذلك:

$array = array ( ‘key1’ => ‘value1’, ‘key2’ => ‘value2’, ‘key3’ => ‘value3’);
extract($array);
echo “$key1 $key2 $key3”;

بعد استدعاء التابع extract()  نكون قد أنشأنا المتغيرات العددية $key1 ,  $key2 ,  $key3  التي لها القيم:  value1 , value2 ,  value3  على التوالي ، وهذه الأسماء والقيم تأتي من المصفوفة الأصلية.
وبالتالي سيكون ناتج هذا الكود هو:
value1 value2 value3

نلاحظ أن التابع   extract() له وسيطين اختياريين هما: extract_type , prefix  

المتغير extract_type :

هذا المتغير يخبر التابع extract()   بالطريقة التي يجب أن يتعامل بها مع حالات التصادم ، حيث تحدث مثل هذه الحالات عندما هناك متغير موجودة مسبقاً يملك نفس اسم المفتاح ، هنا ستكون الاستجابة الافتراضية هي الكتابة فوق المتغير الموجود أي استبدال المتغير الموجود بالمتغير الجديد.
-          EXTR_OVERWRITE : الكتابة فوق المتغير الموجود عند حدوث تصادم.
-          EXTR_SKIP : تخطي العنصر عند حدوث تصادم أي يبقى المتغير الموجود مسبقاً كما هو ولا يتم إنشاء متغير جديد.
-          EXTR_PREFIX_SAME : إنشاء متغير اسمه $prefix_key عند حدوث تصادم وهنا لا بد من تحديد الوسيط الثاني prefix  للتابع extract() .
-          EXTR_PREFIX_ALL : جميع أسماء المتغيرات الجديدة ستبدأ بالبادئة prefix  التي يحددها الوسيط الثاني للتابع extract() .
-          EXTR_PREFIX_INVALID : فقط أسماء المتغيرات التي قد تكون غير صالحة ستبدأ بالبادئة prefix  التي يحددها الوسيط الثاني للتابع extract() .
-          EXTR_IF_EXISTS : استخلاص المتغيرات الموجودة مسبقاً فقط والكتابة فوقها.
-          EXTR_PREFIX_IF_EXISTS : استخلاص المتغيرات الموجودة مسبقاً فقط وإنشاء بادئة لها prefix  يحددها الوسيط الثاني للتابع extract() .
-          EXTR_REFS : استخلاص المتغيرات كمؤشرات.
الخياران الأكثر فائدة هما EXTR_OVERWRITE  (الافتراضي)  و  EXTR_PREFIX_ALL.
مثال على ذلك:

$array = array ( ‘key1’ => ‘value1’, ‘key2’ => ‘value2’, ‘key3’ => ‘value3’);
extract ($array, EXTR_PREFIX_ALL, ‘my_prefix’);
echo “$my_prefix_key1 $my_prefix_key2 $my_prefix_key3”;

هنا جميع أسماء المتغيرات الجديدة ستبدأ بالبادئة my_prefix  بسبب وجود القيمة EXTR_PREFIX_ALL للوسيط الثاني ، و بالتالي سيكون الناتج مرة أخرى من هذا الكود هو:

value1 value2 value3

يجب أن نلاحظ أنه حتى يستطيع التابع ()extract استخراج عنصر ، يجب أن يكون اسم المفتاح المقابل لهذا العنصر اسماً صالحاً مما يعني أنه سيتم تخطي المفاتيح التي تبدأ بالأرقام أو التي تحوي فراغات.

مروان المعلم / ماجستير بالاقتصاد المالي والنقدي
كاتب المقالة
كاتب ومحرر اخبار اعمل في موقع آفاق .

جديد قسم : استخدام لغة PHP

إرسال تعليق