Inilah cara yang sangat bodoh:
def divisorGenerator(n):
for i in xrange(1,n/2+1):
if n%i == 0: yield i
yield n
Hasil yang ingin saya dapatkan mirip dengan yang ini, tetapi saya ingin algoritme yang lebih cerdas (yang ini terlalu lambat dan bodoh :-)
Saya dapat menemukan faktor prima dan multiplisitasnya dengan cukup cepat. Saya memiliki generator yang menghasilkan faktor dengan cara ini:
(faktor1, multiplisitas1)
(faktor2, multiplisitas2)
(faktor3, multiplisitas3)
dan seterusnya ...
yaitu keluaran dari
for i in factorGenerator(100):
print i
adalah:
(2, 2)
(5, 2)
Saya tidak tahu seberapa berguna ini untuk apa yang ingin saya lakukan (saya mengkodekannya untuk masalah lain), bagaimanapun saya ingin cara yang lebih cerdas untuk membuatnya
for i in divisorGen(100):
print i
keluaran ini:
1
2
4
5
10
20
25
50
100
PEMBARUAN: Terima kasih banyak kepada Greg Hewgill dan "cara cerdasnya" :) Menghitung semua pembagi dari 100000000 membutuhkan 0,01 detik dengan caranya melawan angka 39 yang dilakukan oleh cara bodoh pada mesin saya, sangat keren: D
UPDATE 2: Berhenti mengatakan ini adalah duplikat dari posting ini . Menghitung jumlah pembagi dari bilangan tertentu tidak perlu menghitung semua pembaginya. Ini masalah yang berbeda, jika menurut Anda tidak, cari "Fungsi pembagi" di wikipedia. Bacalah soal dan jawabannya sebelum posting, jika belum paham topiknya jangan tambah tidak berguna dan sudah diberi jawaban.
Jawaban:
Mengingat
factorGenerator
fungsi Anda , berikut inidivisorGen
yang harus berfungsi:Efisiensi keseluruhan dari algoritma ini akan bergantung sepenuhnya pada efisiensi dari
factorGenerator
.sumber
Untuk memperluas apa yang dikatakan Shimi, Anda seharusnya hanya menjalankan perulangan dari 1 ke akar kuadrat dari n. Kemudian untuk menemukan pasangannya, lakukan
n / i
, dan ini akan mencakup seluruh ruang masalah.Seperti yang juga dicatat, ini adalah NP, atau masalah 'sulit'. Pencarian menyeluruh, cara Anda melakukannya, sama bagusnya dengan mendapatkan jawaban yang terjamin. Fakta ini digunakan oleh algoritma enkripsi dan sejenisnya untuk membantu mengamankannya. Jika seseorang memecahkan masalah ini, sebagian besar, jika tidak semua, komunikasi 'aman' kita saat ini akan menjadi tidak aman.
Kode Python:
Yang seharusnya menampilkan daftar seperti:
sumber
Meski sudah ada banyak solusi untuk ini, saya benar-benar harus memposting ini :)
Yang ini adalah:
Kode:
sumber
while i*i <= nn
denganwhile i <= limit
, di manalimit = math.sqrt(n)
Saya pikir Anda bisa berhenti di
math.sqrt(n)
bukannya n / 2.Saya akan memberikan contoh agar Anda dapat memahaminya dengan mudah. Sekarang
sqrt(28)
sudah5.29
jadiceil(5.29)
6. Jadi saya jika saya berhenti di 6 maka saya akan bisa mendapatkan semua pembagi. Bagaimana?Pertama lihat kodenya lalu lihat gambar:
Sekarang, lihat gambar di bawah ini:
Katakanlah saya telah menambahkan
1
ke daftar pembagi saya dan saya mulai dengani=2
ituJadi pada akhir semua iterasi karena saya telah menambahkan hasil bagi dan pembagi ke daftar saya, semua pembagi dari 28 diisi.
Sumber: Cara menentukan pembagi suatu bilangan
sumber
math.sqrt(n) instead of n/2
wajib untuk keanggunanSaya suka solusi Greg, tapi saya berharap itu lebih seperti python. Saya merasa ini akan lebih cepat dan lebih mudah dibaca; jadi setelah beberapa waktu pengkodean saya keluar dengan ini.
Dua fungsi pertama diperlukan untuk membuat produk kartesian dari daftar. Dan dapat digunakan kembali setiap kali masalah ini muncul. Ngomong-ngomong, saya harus memprogramnya sendiri, jika ada yang tahu solusi standar untuk masalah ini, jangan ragu untuk menghubungi saya.
"Factorgenerator" sekarang menampilkan kamus. Dan kemudian kamus dimasukkan ke dalam "pembagi", yang menggunakannya untuk menghasilkan daftar pertama, di mana setiap daftar adalah daftar faktor dalam bentuk p ^ n dengan p prime. Kemudian kami membuat perkalian kartesian dari daftar tersebut, dan akhirnya kami menggunakan solusi Greg untuk menghasilkan pembagi. Kami menyortirnya, dan mengembalikannya.
Saya mengujinya dan tampaknya sedikit lebih cepat dari versi sebelumnya. Saya mengujinya sebagai bagian dari program yang lebih besar, jadi saya tidak bisa benar-benar mengatakan berapa cepatnya.
Pietro Speroni (pietrosperoni dot it)
PS ini adalah pertama kalinya saya memposting ke stackoverflow. Saya menantikan tanggapan apa pun.
sumber
Berikut adalah cara cerdas dan cepat untuk melakukannya untuk angka hingga dan sekitar 10 ** 16 dengan Python 3.6 murni,
sumber
Diadaptasi dari CodeReview , berikut adalah varian yang bisa digunakan
num=1
!sumber
NameError: global name 'prime_factors' is not defined
. Tak satu pun dari jawaban lain, atau pertanyaan asli, yang menjelaskan apa yang dilakukannya.Saya hanya akan menambahkan versi Anivarth yang sedikit direvisi (karena saya yakin ini yang paling pythonic) untuk referensi di masa mendatang.
sumber
Pertanyaan lama, tapi inilah pendapat saya:
Anda dapat melakukan proxy dengan:
CATATAN: Untuk bahasa yang mendukung, ini dapat berupa rekursif ekor.
sumber
Dengan asumsi bahwa
factors
fungsi tersebut mengembalikan faktor dari n (misalnya,factors(60)
mengembalikan daftar [2, 2, 3, 5]), berikut adalah fungsi untuk menghitung pembagi dari n :sumber
Inilah solusi saya. Tampaknya bodoh tetapi berfungsi dengan baik ... dan saya mencoba menemukan semua pembagi yang tepat sehingga loop dimulai dari i = 2.
sumber
Jika Anda hanya peduli tentang menggunakan pemahaman daftar dan tidak ada hal lain yang penting bagi Anda!
sumber
Jika PC Anda memiliki banyak memori, satu baris yang kasar bisa cukup cepat dengan numpy:
Membutuhkan waktu kurang dari 1 detik di PC saya yang lambat.
sumber
Solusi saya melalui fungsi generator adalah:
sumber
sumber
Bagi saya ini berfungsi dengan baik dan juga bersih (Python 3)
Tidak terlalu cepat tetapi mengembalikan pembagi baris demi baris seperti yang Anda inginkan, Anda juga dapat melakukan list.append (n) dan list.append (nomor) jika Anda benar-benar ingin
sumber