একবারে দুটি অ্যারে পুনরুক্ত করার 'রুবি উপায়' কী


127

সমস্যার সমাধানের চেয়ে সিনট্যাক্সের আরও কৌতূহল ...

আমার সমান দৈর্ঘ্যের দুটি অ্যারে রয়েছে এবং আমি উভয়কে একবারে পুনরাবৃত্তি করতে চাই - উদাহরণস্বরূপ, একটি নির্দিষ্ট সূচীতে তাদের মানগুলি আউটপুট করতে।

@budget = [ 100, 150, 25, 105 ]
@actual = [ 120, 100, 50, 100 ]

আমি জানি যে আমি each_indexএই জাতীয় অ্যারে ব্যবহার করতে এবং সূচী করতে পারি :

@budget.each_index do |i|
  puts @budget[i]
  puts @actual[i]
end

এটি আরও ভাল করার কোনও রুবি উপায় আছে? এরকম কিছু ?

# Obviously doesn't achieve what I want it to - but is there something like this?
[@budget, @actual].each do |budget, actual|
  puts budget
  puts actual
end

1
উভয়ই সমান আকারের অ্যারে?
— অনুরাগ

1
হ্যাঁ - উভয়ই একই দৈর্ঘ্যের হিসাবে পরিচিত
— nfm

উত্তর:


276
>> @budget = [ 100, 150, 25, 105 ]
=> [100, 150, 25, 105]
>> @actual = [ 120, 100, 50, 100 ]
=> [120, 100, 50, 100]

>> @budget.zip @actual
=> [[100, 120], [150, 100], [25, 50], [105, 100]]

>> @budget.zip(@actual).each do |budget, actual|
?>   puts budget
>>   puts actual
>> end
100
120
150
100
25
50
105
100
=> [[100, 120], [150, 100], [25, 50], [105, 100]]

12
'.আচ' অ্যারে উপাদানগুলি উদ্ঘাটন করতে পারে? আমি অবাক হয়ে দেখি রুবি কত বেশি জানি না: /
— নিকিতা রাইবাক

5
আপনি যদি এর মতো একটি এক্সপ্রেশন ব্যবহার করতে যাচ্ছেন তবে কেবলমাত্র ক্ষেত্রে, পদ্ধতি কলগুলির জন্য প্রথম বন্ধনী ব্যবহার করা সর্বদা সেরা। @ বাজেট.জিপ (@ বাস্তব) .ইচ
— রবি

1
@ অ্যাবাউটরুবি: এই ক্ষেত্রে, এটি প্রয়োজন! সংশোধন করা হয়েছে।
— মার্ক-আন্দ্রে লাফোর্টুন

2
আমি যখন রুব্বি রেখাগুলি দেখি, তখন আমার হাত বাতাসে ফেলে দেয় এবং ঘরের মতো ঘুরে বেড়ায়!
— আইগবানাম

9
এই স্কেল না? আমার কাছে যদি 10000 আইটেম অ্যারে থাকে তবে এর জন্য কি 20,000 আইটেম অ্যারে তৈরি করা দরকার? ডক্স এটি পরামর্শ দেয় suggest
— টম অ্যান্ডারসন

21

Array.zipপদ্ধতিটি ব্যবহার করুন এবং এটিকে যথাযথভাবে সম্পর্কিত উপাদানগুলির উপর পুনরাবৃত্তি করতে একটি ব্লকটি দিন।


20

গণক ব্যবহার করে একবারে দুটি অ্যারে পুনরাবৃত্তি করার অন্য উপায় রয়েছে:

2.1.2 :003 > enum = [1,2,4].each
 => #<Enumerator: [1, 2, 4]:each> 
2.1.2 :004 > enum2 = [5,6,7].each
 => #<Enumerator: [5, 6, 7]:each> 
2.1.2 :005 > loop do
2.1.2 :006 >     a1,a2=enum.next,enum2.next
2.1.2 :007?>   puts "array 1 #{a1} array 2 #{a2}"
2.1.2 :008?>   end
array 1 1 array 2 5
array 1 2 array 2 6
array 1 4 array 2 7

উপরে উল্লিখিত উদাহরণগুলির তুলনায় গণকরা আরও শক্তিশালী, কারণ তারা অন্যান্য কৌশলগুলির মধ্যে অসীম সিরিজ, সমান্তরাল পুনরাবৃত্তির অনুমতি দেয়।


1
loopউপরে দেখানো ভিতরে সূচক পাওয়ার কোনও উপায় আছে কি ?
— বিজু

16

a.zip(b).each{|x,y| }অন্যেরা যেমন বলেছে তা ছাড়াও , আপনি এটিও বলতে পারেন [a,b].transpose.each{|x,y| }, যা আমাকে আরও সামান্য সাম্প্রতিক হিসাবে আঘাত করে। আপনি অতিরিক্ত [a,b]অ্যারে তৈরি করার পরে সম্ভবত সম্ভবত তত দ্রুত নয় ।


11
+1 সম্পর্কে সুন্দর জিনিসগুলির মধ্যে একটি transposeহ'ল যদি দুটি অ্যারে একই দৈর্ঘ্য না হয় তবে এটি ব্যতিক্রম করে।
— অ্যান্ড্রু গ্রিম

14

মূল প্রশ্নের সাথে সম্পর্কিত, অসম দৈর্ঘ্যের অ্যারেগুলিকে পুনরাবৃত্তি করার জন্য যেখানে আপনি নিজের চারপাশের মানগুলি ব্যবহার করতে চান

[1,2,3,4,5,6].zip([7,8,9].cycle)

এবং রুবি আপনাকে দেবে

[[1, 7], [2, 8], [3, 9], [4, 7], [5, 8], [6, 9]]

এটি আপনাকে nilকেবলমাত্র জিপ ব্যবহারের মাধ্যমে যে মানগুলি পেতে হবে তা থেকে রক্ষা করে


6

আপনি যদি অ্যারে নিয়ে কাজ করছেন তবে কেবল দুটি অ্যারে জিপ করা ভালভাবে কাজ করে। তবে যদি আপনি কখনই শেষ না হওয়া গণকের সাথে এই জাতীয় কিছু ব্যবহার করছেন:

enum1 = (1..5).cycle
enum2 = (10..12).cycle

enum1.zip(enum2)ব্যর্থ হয় কারণ zipসমস্ত উপাদানগুলির মূল্যায়ন এবং তাদের একত্রিত করার চেষ্টা করে। পরিবর্তে, এটি করুন:

enum1.lazy.zip(enum2)

এক যে lazyফলে গণনাকারী অলস মূল্যায়ন করার ফলে আপনাকে পরিমাণ সঞ্চয় হয়।


2

কীভাবে আপস করা, এবং # ইচ্ছু_বিহীন_আইডেক্স ব্যবহার সম্পর্কে?

include Enumerable 

@budget = [ 100, 150, 25, 105 ]
@actual = [ 120, 100, 50, 100 ]

@budget.each_with_index { |val, i| puts val; puts @actual[i] }
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.