اذهب إلى المحتوى

السؤال

نشر

 

كيف يمكنني إعادة ترتيب عناصر مصفوفة في NumPy حسب العمود n مثلًا؟

على سبيل المثال لدي المصفوفة التالية:

arr = array([[9, 2, 3],
           [4, 5, 6],
           [7, 0, 5]])

كيف يمكنني ترتيب الصفوفة وفقًا لقيم العمود الثاني؟ لتكون النتيجة كالتالي:

array([[7, 0, 5],
       [9, 2, 3],
       [4, 5, 6]])

 

Recommended Posts

  • 0
نشر

يمكن تطبيق التعليمة التالية للترتيب حسب العمود الثاني حيث تم تمرير الرقم 1 كدليل للعمود (0 دليل أول عمود)

a[a[:, 1].argsort()]

ويمكن أيضا باستخدام معامل lambda:

a = sorted(a, key=lambda a_entry: a_entry[1]) 

حيث أن a_entry[1] تمثل الععود المراد الترتيب وفقه

الدالة argsort تقوم بعمل ترتيب لمصفوفة numpy حسب الدليل الممر لها

  • 0
نشر

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

In [1]: import numpy as np

In [2]: a = np.array([[1,2,3],[4,5,6],[0,0,1]])

In [3]: np.sort(a.view('i8,i8,i8'), order=['f1'], axis=0).view(np.int)
Out[3]: 
array([[0, 0, 1],
       [1, 2, 3],
       [4, 5, 6]])

اما لترتيبها في نفس مكانها:

In [6]: a.view('i8,i8,i8').sort(order=['f1'], axis=0) 

In [7]: a
Out[7]: 
array([[0, 0, 1],
       [1, 2, 3],
       [4, 5, 6]])

الميزة الوحيدة لهذه الطريقة هي أن طريقة "الترتيب" هي قائمة بالحقول لترتيب البحث. على سبيل المثال ، يمكنك الفرز حسب العمود الثاني ، ثم العمود الثالث ، ثم العمود الأول من خلال تقديم الترتيب = ['f1' ، 'f2' ، 'f0'].

  • 1
نشر

لفرز عناصر مصفوفة هناك عدة طرق للقيام بذلك، أولها استخدام التابع argsort من نمباي، حيث يعيد مؤشرات أو فهارس من المصفوفة، هذه المؤشرات يمكننا استخدامها لترتيب مصفوفتنا، سأعطيك الآن مثال لكيفية الاستفادة من هذا. لتكن لدينا المصفوفة التالية:

import numpy as np
a = np.random.randint(70, size=(3, 3))
a
"""
array([[ 0, 33, 32],
       [53, 44,  4],
       [36, 34,  0]])
"""

سنقوم أولاً باستعداء التابع argsort على العمود الأول من المصفوفة، وبالتالي ستحصل على هذه النتيجة:

a[:, 0].argsort()
#  array([0, 2, 1], dtype=int64)

يوضح الخرج أن أصغر قيمة في العمود الأول هي في الموضع 0 (رقم السطر الموجودة فيه). وهذا صحيح ، فأقل قيمة في العمود الأول للمصفوفة هي 0، أما ثاني قيمة من الخرج هي 2 وهذا يعني أن ثاني أصغر قيمة في العمود الأول موجودة في الموضع 2 أي القيمة الثالثة أي 36 وهذا صحيح. أما ثالث قيمة من الخرج فتشير إلى ثالث أصغر قيمة في العمود وهكذا..، لفرز المصفوفة ، نحتاج الآن إلى استخدام المؤشرات التي أعطانا إياها التابع argsort لإعادة ترتيب الصفوف في المصفوفة. ويمكننا القيام بذلك عبر إجراء بسيط يمكن القيام به في سطر واحد من التعليمات البرمجية. إذاً سنستخدم نتيجة argsort على أنها فهارس الصف وسنضع الناتجة في a (مصفوفتنا) ، على النحو التالي:

a = a[a[:, 0].argsort()]
a
"""
array([[ 0, 33, 32],
       [36, 34,  0],
       [53, 44,  4]])
"""

كما ترى، تم ترتيب الصفوف الآن من الأقل إلى الأكبر وفقاً للعمود الأول. وللفرز في عمود مختلف، ما عليك سوى تغيير فهرس العمود.

a = a[a[:, 1].argsort()]
a
"""
array([[ 0, 33, 32],
       [53, 34,  0],
       [36, 44,  4]])
"""

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

import numpy as np
a = np.random.randint(70, size=(3, 3))
a
"""
array([[44, 10, 23],
       [ 9, 32, 58],
       [67, 31, 39]])
"""
a = a[:, a[0, :].argsort()]
a
"""
array([[10, 23, 44],
       [32, 58,  9],
       [31, 39, 67]])
"""

في بعض الأحيان يكون من الضروري الفرز على أكثر من عمود واحد. أحد الأمثلة على ذلك هو البيانات التي تحتوي على السنة والشهر واليوم والقيمة في أعمدة منفصلة. يمكن أن يتعامل ترتيب Argsort في NumPy مع فرز أعمدة متعددة باستخدام الوسيطة اللطيفة. لنبدأ بإنشاء مصفوفة من 4 أعمدة تمثل السنة والشهر واليوم والقيمة.

arr = np.array([[2019, 2, 1, 40],
              [2021, 4, 1, 80],
              [2020, 3, 2, 22],
              [2018, 1, 3, 11],
              [2021, 3, 9, 79]])
"""
array([[2018,    1,    3,   11],
       [2019,    2,    1,   40],
       [2020,    3,    2,   22],
       [2021,    3,    9,   79],
       [2021,    4,    1,   80]])
"""

سنستخدم الآن argsort لفرز الأعمدة ، بدءاً من الأولوية الأقل. هذا يعني أننا إذا أردنا الفرز حسب السنة ، ثم الشهر ، ثم اليوم ، فنحن بحاجة إلى الفرز حسب اليوم أولاً ، ثم الشهر ، ثم العام. بالنسبة للكل ما عدا النوع الأول ، نحتاج إلى تحديد النوع على أنه "ترتيب مدمج" ، والذي سيحافظ على سياق الفرز السابق. وهذا موضح في التعليمات البرمجية التالية:

 # الفرز حسب اليوم
arr = arr[arr[:, 2].argsort()] 
# حسب الششهر
arr = arr[arr[:, 1].argsort(kind='mergesort')] 
# حسب السنة
arr = arr[arr[:, 0].argsort(kind='mergesort')]  

يمكنك استخدام طرق أخرى أعقد أيضاً مثل استخدام lexsort من نمباي كما في المثال التالي:

import numpy as np
a = np.random.randint(70, size=(3, 3))
a
"""
array([[12, 11,  6],
       [25, 46, 64],
       [42, 41,  1]])
"""
col=0
a[np.lexsort(([1,-1]*a[:,[1,col]]).T)]
"""
array([[42, 41,  1],
       [25, 46, 64],
       [12, 11,  6]])
"""

أو يمكنك باستخدام الدالة sorted مع الوسيط لامدا، وتعيد قائمة (لذا قم بإعادة تحويل الخرج إلى نمباي):

import numpy as np
a = np.random.randint(70, size=(3, 3))
a
"""
array([[17, 46, 17],
       [39, 64, 54],
       [ 6, 19, 68]])
"""
col=1 # العمود المراد الترتيب عليه
a=sorted(a, key=lambda a_entry: a_entry[col]) 
np.array(a)
"""
[[ 6 19 68]
 [17 46 17]
 [39 64 54]]

"""

هذا كان كل ماقد يلزمك.

انضم إلى النقاش

يمكنك أن تنشر الآن وتسجل لاحقًا. إذا كان لديك حساب، فسجل الدخول الآن لتنشر باسم حسابك.

زائر
أجب على هذا السؤال...

×   لقد أضفت محتوى بخط أو تنسيق مختلف.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   جرى استعادة المحتوى السابق..   امسح المحرر

×   You cannot paste images directly. Upload or insert images from URL.

  • إعلانات

  • تابعنا على



×
×
  • أضف...