2012-01-19 11 views
51

Diyelim ki a = [1,1,1,2,2,3] dizisinden öğeleri kaldırmaya çalışıyorum. Aşağıdaki gerçekleştirirseniz:Öğe Kalecinden öğeleri kaldırma Ruby

b = a - [1,3] 

Sonra alacak:

b = [2,2] 

Ancak, ben

b = [1,1,2,2] 

yani sadece her elemanın bir örneğini kaldırmak sonucu olmak istiyorum çıkarılmış vektör tüm durumlar değil. Bunu yapmak için Ruby'de basit bir yol var mı?

+0

sen çıkarma eğer '[1,1,3]' sen bitirmek istiyoruz b = [1,2,2] 'ile yukarı? Yoksa bu asla olmayacak mı? – seph

cevap

63

Sen yapabilirsiniz:

a= [1,1,1,2,2,3] 
delete_list = [1,3] 
delete_list.each do |del| 
    a.delete_at(a.index(del)) 
end 

sonuç: [1, 1, 2, 2]

+1

Yani dizi çıkarma işlemi aslında ayrılmıyor mu? –

+1

Dizi Farkı --- Orijinal dizinin bir kopyası olan yeni bir diziyi döndürür, diğer metinlerde de görünen öğeleri kaldırır. (Set benzeri davranışa ihtiyacınız varsa, Set kütüphanesi sınıfına bakın.) [Link] (http://www.ruby-doc.org/core-1.9.3/Array.html) – Norm212

+2

Tüm örnekleri kaldırmak istiyorsanız "delete_list" öğesindeki öğeler, bunu yapabilirdiniz. 'b = a.each.reject {| x | delete_list.each.include? x} ' – Archonic

2
çok basit değil

ama:

a = [1,1,1,2,2,3] 
b = a.group_by {|n| n}.each {|k,v| v.pop [1,3].count(k)}.values.flatten 
=> [1, 1, 2, 2] 

Ayrıca katları için durum kolları 'subtrahend':

a = [1,1,1,2,2,3] 
b = a.group_by {|n| n}.each {|k,v| v.pop [1,1,3].count(k)}.values.flatten 
=> [1, 2, 2] 

DÜZENLEME: bu mor Norm212'yi ve cevabımı "işlevsel" bir çözüm yapmak için birleştiren bir geliştirme. Gerekirse

b = [1,1,3].each.with_object(a) { |del| a.delete_at(a.index(del)) } 

bir lambda koy: o zaman

subtract = lambda do |minuend, subtrahend| 
    subtrahend.each.with_object(minuend) { |del| minuend.delete_at(minuend.index(del)) } 
end 

:

subtract.call a, [1,1,3] 
+0

Hayır, sipariş değiştirilmiş olabilir. Norm212'nin siparişi koruduğu anlaşılıyor. – seph

+0

@Michael lütfen düzenlemeleri inceleyin – seph

3
[1,3].inject([1,1,1,2,2,3]) do |memo,element| 
    memo.tap do |memo| 
    i = memo.find_index(e) 
    memo.delete_at(i) if i 
    end 
end 
İlgili konular