Cara yang benar untuk mengisi Array dengan Range di Ruby


201

Saya sedang mengerjakan buku yang memberikan contoh Ranges yang dikonversi ke array yang setara menggunakan metode "to_a" mereka

Ketika saya menjalankan kode di irb saya mendapatkan peringatan berikut

 warning: default `to_a' will be obsolete

Apa alternatif yang tepat untuk menggunakan to_a?

Adakah cara alternatif untuk mengisi array dengan Range?


7
Peringatan besar untuk mengonversi rentang ke array, adalah rentang besar dapat mengkonsumsi banyak memori saat array dibangun, jadi gunakan dengan hati-hati. Alih-alih membuat array, mungkin lebih baik untuk mengulangi rentang seperti halnya array agar konsumsi memori tetap rendah. Ini adalah salah satu dari hal-hal "berlaku seperlunya".
the Tin Man

Jawaban:


357

Anda dapat membuat array dengan rentang menggunakan percikan,

>> a=*(1..10)
=> [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

menggunakan Kernel Arraymetode,

Array (1..10)
=> [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

atau menggunakan to_a

(1..10).to_a
=> [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

1
Bagaimana jika array sudah dibuat dan Anda ingin menambahkan rentang ke sana: Saya punya order = 1. Lalu order << (2.25).to_a. Tapi ini menciptakan array lain di dalam array, saya hanya ingin rentang dari 2 hingga 25. Namun jika saya coba order << (2.25)saya mendapatkan kesalahan tidak dapat mengubah Range menjadi Integer.
kakubei

1
@kakubei digunakan concatsebagai gantinya <<. Selain itu, Anda seharusnya tidak mendapatkan "tidak dapat mengubah Rentang ke Integer" kecuali orderbilangan bulat - dalam hal ini Anda akan menggeser bit, bukan menambahkan array.
Kelvin

3
opsi Splat tidak berfungsi untuk Ruby 1.8.7, saya akan merekomendasikan penggunaan (1..10).to_auntuk kompatibilitas mundur
kylewelsby

5
Penggunaan splat Anda tidak menyenangkan. Pilihan yang terlihat lebih baik adalah [*1..10].
Hauleth

2
apa cara tercepat ??
Andrey Yasinishyn

79

Ini bekerja untuk saya di irb:

irb> (1..4).to_a
=> [1, 2, 3, 4]

Saya melihat itu:

irb> 1..4.to_a
(irb):1: warning: default `to_a' will be obsolete
ArgumentError: bad value for range
        from (irb):1

Jadi mungkin Anda kehilangan tanda kurung?

(Saya menjalankan Ruby 1.8.6 patchlevel 114)


7
Penjelasan : tanpa tanda kurung, Anda memanggil metode to_a dari turunan Kelas Fixnum (dalam kasus ini 4), bukan pada kisaran 1..4. Jika Anda menjalankan Fixnum.methods.include?(to_a)di ruby ​​1.9.2 Anda akan melihat bahwa metode to_a tidak lagi didefinisikan, maka mengapa Anda mendapatkan pesan penyusutan di 08
Pierre

@Ier saya pikir Anda maksudFixnum.instance_methods.include?(:to_a)
Kelvin

@Kelvin - Sebenarnya, methods.include?lebih informatif: $ irb irb(main):001:0> Fixnum.methods.include?(to_a) (irb):1: warning: default to_a 'akan usang=> false irb(main):002:0> Fixnum.instance_methods.include?(:to_a) => false
Richard Turner

1
@ RichardTurner Saya menganggap Anda menggunakan ruby ​​1.8. Saya khawatir Anda salah memahami apa yang memicu to_aperingatan di formulir pertama. Itu karena Anda menelepon to_apada self- Anda tidak benar-benar memeriksa apakah to_aadalah metode Fixnum. Coba panggil to_adengan sendirinya dan Anda akan melihat peringatan yang sama.
Kelvin

@Kelvin - Duh! Uang receh itu jatuh. Terima kasih.
Richard Turner

34

Sepertinya Anda melakukan ini:

0..10.to_a

Peringatan ini dari Fixnum # to_a, bukan dari Range # to_a. Coba ini sebagai gantinya:

(0..10).to_a



4

Saya hanya mencoba menggunakan rentang dari jumlah yang lebih besar ke yang lebih kecil dan mendapatkan hasil yang tidak saya harapkan:

irb(main):007:0> Array(1..5)
=> [1, 2, 3, 4, 5]
irb(main):008:0> Array(5..1)
=> []

Itu karena implementasi rentang.
Jadi saya harus menggunakan opsi berikut:

(1..5).to_a.reverse

4
Hari ini saya menemukan 5.downto(1).to_ayang merupakan cara lain untuk mengekspresikan jangkauan stackoverflow.com/a/8927009/703903 yang
odlp
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.