Intro
Pertimbangkan proses mengambil bilangan bulat positif n di beberapa basis b dan mengganti setiap digit dengan perwakilannya di dasar digit di sebelah kanan.
- Jika digit di sebelah kanan adalah 0, gunakan basis b .
- Jika digit di sebelah kanan adalah 1, gunakan unary dengan 0 sebagai tanda penghitungan.
- Jika tidak ada digit di sebelah kanan (yaitu Anda berada di tempat yang), lilitkan ke digit yang paling signifikan.
Sebagai contoh, mari n = 160 dan b = 10. Menjalankan prosesnya terlihat seperti ini:
The first digit is 1, the digit to the right is 6, 1 in base 6 is 1.
The next digit is 6, the digit to the right is 0, 0 is not a base so use b, 6 in base b is 6.
The last digit is 0, the digit to the right (looping around) is 1, 0 in base 1 is the empty string (but that's ok).
Concatenating '1', '6', and '' together gives 16, which is read in the original base b = 10.
Prosedur yang persis sama tetapi bergerak ke kiri dan bukan ke kanan juga dapat dilakukan:
The first digit is 1, the digit to the left (looping around) is 0, 0 is not a base so use b, 1 in base b is 1.
The next digit is 6, the digit to the left is 1, 6 in base 1 is 000000.
The last digit is 0, the digit to the left is 6, 0 in base 6 is 0.
Concatenating '1', '000000', and '0' together gives 10000000, which is read in the original base b = 10.
Dengan demikian, kami telah membuat dua angka yang terkait dengan 160 (untuk b = 10): 16 dan 10.000000.
Kami akan mendefinisikan n sebagai angka yang licik jika membagi secara merata setidaknya satu dari dua angka yang dihasilkan dalam proses ini menjadi 2 atau lebih bagian
Dalam contoh n adalah licik karena 160 membagi 10.000.000 persis 62500 kali.
203 BUKAN licik karena angka yang dihasilkan adalah 2011 dan 203 itu sendiri, yang 203 tidak bisa masuk secara merata menjadi 2 atau lebih kali.
Tantangan
(Untuk sisa masalah, kami hanya akan mempertimbangkan b = 10.)
Tantangannya adalah untuk menulis sebuah program yang menemukan angka licik tertinggi yang juga prima.
7 prima licik pertama (dan semua yang saya temukan sejauh ini) adalah:
2
5
3449
6287
7589
9397
93557 <-- highest so far (I've searched to 100,000,000+)
Saya tidak yakin secara resmi apakah lebih ada, tetapi saya berharap mereka ada. Jika Anda dapat membuktikan bahwa ada (atau tidak) yang banyak, saya akan memberi Anda +200 rep bounty.
Pemenangnya adalah orang yang dapat memberikan prime licik tertinggi, asalkan jelas bahwa mereka telah aktif dalam pencarian dan tidak sengaja mengambil kemuliaan dari orang lain.
Aturan
- Anda dapat menggunakan alat temuan utama apa pun yang Anda inginkan.
- Anda dapat menggunakan penguji utama probabilistik.
- Anda dapat menggunakan kembali kode orang lain dengan atribusi . Ini adalah upaya bersama. Taktik kejam tidak akan ditoleransi.
- Program Anda harus secara aktif mencari yang utama. Anda dapat memulai pencarian di prime licik yang paling dikenal.
- Program Anda harus dapat menghitung semua prima licik yang dikenal dalam waktu 4 jam dari Amazon EC2 t2.medium instance (baik empat sekaligus atau satu selama empat jam atau sesuatu di antaranya). Saya sebenarnya tidak akan mengujinya pada Anda dan Anda tentu tidak perlu. Ini hanya tolok ukur.
Berikut ini adalah kode Python 3 yang saya gunakan untuk membuat tabel di atas: (berjalan dalam satu atau dua detik)
import pyprimes
def toBase(base, digit):
a = [
['0', '1', '2', '3', '4', '5', '6', '7', '8', '9'],
['', '0', '00', '000', '0000', '00000', '000000', '0000000', '00000000', '000000000' ],
['0', '1', '10', '11', '100', '101', '110', '111', '1000', '1001'],
['0', '1', '2', '10', '11', '12', '20', '21', '22', '100'],
['0', '1', '2', '3', '10', '11', '12', '13', '20', '21'],
['0', '1', '2', '3', '4', '10', '11', '12', '13', '14'],
['0', '1', '2', '3', '4', '5', '10', '11', '12', '13'],
['0', '1', '2', '3', '4', '5', '6', '10', '11', '12'],
['0', '1', '2', '3', '4', '5', '6', '7', '10', '11'],
['0', '1', '2', '3', '4', '5', '6', '7', '8', '10']
]
return a[base][digit]
def getCrafty(start=1, stop=100000):
for p in pyprimes.primes_above(start):
s = str(p)
left = right = ''
for i in range(len(s)):
digit = int(s[i])
left += toBase(int(s[i - 1]), digit)
right += toBase(int(s[0 if i + 1 == len(s) else i + 1]), digit)
left = int(left)
right = int(right)
if (left % p == 0 and left // p >= 2) or (right % p == 0 and right // p >= 2):
print(p, left, right)
if p >= stop:
break
print('DONE')
getCrafty()
sumber
Jawaban:
Mathematica, temukan 93.557 dalam 0,3 detik (tidak ada bilangan prima lebih lanjut di bawah 2 * 10 10 )
Ini hanya pencarian lengkap yang naif melalui semua bilangan prima. Untuk mulai dengan itu memeriksa sekitar 1.000.000 bilangan prima setiap 55 detik (yang pasti akan semakin lambat karena bilangan prima menjadi lebih besar).
Saya menggunakan banyak fungsi pembantu:
Dan kemudian loop ini melakukan pencarian yang sebenarnya:
Saya akan terus memperbarui posting, jika saya menemukan bilangan prima atau dapat memikirkan optimisasi.
Saat ini memeriksa semua bilangan prima hingga 100.000.000 dalam waktu sekitar 5,5 menit.
Sunting: Saya memutuskan untuk mengikuti contoh OP dan beralih ke tabel pencarian untuk konversi basis. Itu memberi sekitar 30% percepatan.
Angka licik secara umum
Saya menghentikan pencarian saya untuk bilangan prima licik sekarang, karena saya perlu beberapa hari hanya untuk mengejar ketinggalan dari mana jawaban Perl sudah didapat. Sebaliknya, saya mulai mencari semua angka licik. Mungkin distribusi mereka membantu menemukan bukti bahwa jumlah prima licik adalah terbatas atau tidak terbatas.
Saya mendefinisikan angka licik kanan yang membagi angka terkait yang diperoleh dengan menafsirkan angka di sebelah kanan sebagai basis baru, dan angka licik kiri sesuai. Mungkin akan membantu untuk mengatasi ini secara individual sebagai bukti.
Berikut adalah semua angka licik kiri hingga 2.210.000.000:
Dan di sini ada semua angka licik di kisaran itu:
Perhatikan bahwa ada angka tak terbatas nomor kiri-licik dan licik, karena ada beberapa cara untuk menghasilkan mereka dari yang ada:
0
s ke angka licik kiri mana digit paling signifikan lebih besar dari digit paling signifikan untuk mendapatkan angka licik kiri lainnya.0
s ke angka licik mana pun yang digit paling signifikan kurang dari digit paling signifikan. Ini (dan pernyataan sebelumnya) adalah karena0
akan ditambahkan ke nomor licik dan nomor terkait, secara efektif mengalikan keduanya dengan 10.2
s atau5
s adalah licik.777
adalah licik.28
bergabung dengan0
s, seperti28028028
selalu licik.Hal-hal lain yang perlu diperhatikan:
125
. Mungkin perlu menyelidiki mereka untuk menemukan aturan produksi lain.Saya kira daftar ini akan lebih menarik jika saya menghilangkan mereka yang keberadaannya tersirat oleh angka licik yang lebih kecil, terutama karena ini tidak pernah menjadi bilangan prima oleh aturan konstruksi yang ditemukan sejauh ini. Jadi di sini adalah semua bilangan prima licik yang tidak dapat dibangun dengan salah satu aturan di atas:
Perhatikan juga bahwa ada beberapa angka licik ganda (yang muncul di kedua daftar dan karenanya membagi kedua angka terkait):
Ada banyak hal yang tak terhingga juga.
Tapi seperti yang Anda lihat, kecualiMenemukan contoh tandingan16
,28
,68
ini semua hanya terdiri dari (diulang) digit tunggal. Ini juga akan menarik untuk membuktikan apakah angka yang lebih besar dapat menjadi dua kali lipat licik tanpa memiliki properti itu, tetapi itu mungkin hanya akan keluar sebagai akibat wajar dari bukti angka tunggal yang licik.1944919449
.sumber
100540625, 100540625
dalam daftar licik Anda?Perl (1e5 dalam 0,03s, 1e8 dalam 21s). Maks 93557 hingga 1e11.
Sangat mirip dengan aslinya. Perubahan meliputi:
Melakukan prie 1e8 pertama dalam 21 detik pada mesin cepat saya, 3,5 menit untuk 1e9, 34 menit untuk 1e10. Saya sedikit terkejut itu sama sekali lebih cepat daripada kode Python untuk input kecil. Kita bisa memparalelkan (Pari / GP baru
parforprime
akan bagus untuk ini). Karena ini adalah pencarian, kita dapat memparalelkan dengan tangan saya kira (forprimes
dapat mengambil dua argumen).forprimes
pada dasarnya seperti Pari / GPforprime
- itu memang saringan tersegmentasi secara internal dan memanggil blok dengan setiap hasil. Memang nyaman, tetapi untuk masalah ini saya tidak berpikir itu adalah area kinerja.sumber
C ++ 11, dengan utas dan GMP
Pengaturan Waktu (di MacBook Air):
Persyaratan:
g++ crafty.cpp -o crafty --std=c++11 -ffast-math -lprimesieve -O3 -lgmpxx -lgmp -Wall -Wextra
Keluaran:
sumber
C, dengan GMP, multithreaded (1e8 in 17s for 1 thread)
Mirip dalam konsep dengan yang lain, dengan mungkin sedikit optimasi di sana-sini.
Menyusun:
gcc -I/usr/local/include -Ofast crafty.c -pthread -L/usr/local/lib -lgmp && ./a.out
Mohon donasikan kekuatan CPU Anda. Saya tidak punya komputer yang cepat.
1e8 dalam 17 detik dengan 1 utas di macbook air saya.
sumber
Python, menemukan 93557 dalam 0,28s
Sangat mirip dengan kode OP yang digunakannya
pyprimes
. Saya menulis ini sendiri meskipun xDIni juga mencetak waktu sejak awal yang menemukan nomor.
Keluaran:
Formatnya adalah
number left right time
. Sebagai perbandingan, kode OP menemukan 93557 di sekitar0.37
.sumber