الفرز روبي مجموعة من الأشياء من قبل السمة التي يمكن النيل

StackOverflow https://stackoverflow.com/questions/808318

  •  03-07-2019
  •  | 
  •  

سؤال

لدي مجموعة من الكائنات التي تحتاج إلى فرز حسب الموقف السمة التي يمكن أن يكون عدد صحيح أو النيل, و أنا في حاجة إلى الكائنات التي النيل يمكنها من أن تكون في نهاية الصفيف.الآن أستطيع أن قوة الموقف إلى عودة بعض القيمة بدلا من النيل حتى مجموعة.نوع لا تفشل ، ولكن إذا كنت تستخدم 0 كما أن هذا التقصير ، ثم يضع هذه الأشياء في الجزء الأمامي من هذا النوع.ما هي أفضل طريقة للقيام بذلك النوع ؟ يجب أن مجرد مجموعة النيل القيم إلى بعض عالية يبعث على السخرية رقم 'تقريبا' يضمن دائما أن يكون في نهاية المطاف ؟ أو هل هناك طريقة أخرى أنا يمكن أن تسبب مجموعة.نوع الأسلوب لوضع النيل سمة الكائنات في نهاية المصفوفة ؟ رمز يبدو مثل هذا:

class Parent
  def sorted_children
     children.sort{|a, b| a.position <=> b.position}
  end
end

class Child
  def position
    category ? category.position : #what should the else be??
  end
end

الآن, إذا كنت جعل 'آخر' شيء مثل 1000000000 ، ثم إنه على الأرجح سوف وضعها في نهاية المصفوفة, ولكن أنا لا أحب هذا الحل كما انها التعسفي

هل كانت مفيدة؟

المحلول

وماذا عن في Child تحديد <=> أن تستند category.position في حالة وجود category، وفرز العناصر دون category كما أكبر دائما من أولئك الذين لديهم category؟

class Child
  # Not strictly necessary, but will define other comparisons based on <=>
  include Comparable   
  def <=> other
    return 0 if !category && !other.category
    return 1 if !category
    return -1 if !other.category
    category.position <=> other.category.position
  end
end

وبعد ذلك في Parent يمكنك الاتصال فقط children.sort.

نصائح أخرى

وأود فقط قرص نوع لوضع البنود nil الماضي. محاولة شيء من هذا القبيل.

foo = [nil, -3, 100, 4, 6, nil, 4, nil, 23]

foo.sort { |a,b| a && b ? a <=> b : a ? -1 : 1 }

=> [-3, 4, 4, 6, 23, 100, nil, nil, nil]

وهذا يقول: إذا أ و ب على حد سواء غير شيء الفرز لهم عادة ولكن إذا واحد منهم هو لا شيء، والعودة إلى الوضع الذي يفرز أن أحد أكبر

.

أنا التعامل مع هذه الأنواع من الأشياء من هذا القبيل:

 children.sort_by {|child| [child.position ? 0 : 1,child.position || 0]}

لنكون منصفين، وأنا لست على دراية جدا مع روبي، حتى تأخذ هذا الأمر أكثر من فكرة الخوارزمية بدلا من رمز واحد ... وإعادة كتابة: مشغل ما أن ما لديها روبي هذا أنظف

.

ولا يمكنك فقط التحقق من وجود شيء في المقارنة:

class Parent
  def sorted_children
     children.sort{|a,b|( a and b ) ? a <=> b : ( a ? -1 : 1 ) }
  end
end

وقام لاستخدام رمز Glenra، والتي تطبق نفس الشيء مثل الألغام ولكن في كمية أقل (وربما أسهل في القراءة) من التعليمات البرمجية.

وأنا لم تكن قد فعلت روبي في حين، ولكن هل يمكن تقسيم خالية التحقق من الفرز (والسماح فقط للأطفال # موقف للعودة لاغية):

def sorted_children
  children.reject{|c| c.position.nil?}.sort_by(&:position) +
    children.select{|c| c.position.nil?}
end

وباعتراف الجميع انها ليست الحل الأكثر فعالية، ولكن ليس لديها أي أرقام سحرية.

ويمكنك القيام بذلك دون تجاوز مشغل سفينة الفضاء عن طريق تحديد طريقة المقارنة جديد.

class Child
  include Comparable   
  def compare_by_category(other)
    return 0 if !category && !other.category
    return 1 if !category
    return -1 if !other.category
    category.position <=> other.category.position
  end
end

وطريقة sort يمكن أن كتلة، لذلك يمكنك بعد ذلك النوع باستخدام هذه الطريقة الجديدة:

children.sort {|a,b| a.compare_by_category(b) }

والحل أبسط بالنسبة لي هو

def sorted_children(children)
  children.sort_by { |child| child.position || -1}
end
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top