Belirli bir LCM ve GCD ile sayı çiftlerini bulun


9

Bir arkadaşımla matematik sorusu üzerinde çalışıyordum ve cevabı bulan bir senaryo yazmaya karar verdik. Orijinal soru aşağıdaki gibidir:

İki doğal sayının farkı 2010 ve en büyük ortak paydaları, en düşük ortak çarpanlarından 2014 kat daha küçüktür. Olası tüm çözümleri bulun.

Programı birbirinden bağımsız olarak yazmaya başladık ve çalıştığında yönetebileceğimiz en az miktarda baytı elde etmek için golf oynamaya karar verdik. Biz muhteşem 89 bayt bu güzel kod satırı ile sona erdi.

from fractions import*;print[i for i in range(10**6)if i*(i+2010)/gcd(i,i+2010)**2==2014]

Kimse daha kısa bir kod parçası yazmayı başarabildiğini, ilk 1 milyonu numaralandıran görmek istedik. Yarışmak için yeterince cesursanız, istediğiniz herhangi bir dili kullanabilirsiniz, ancak Python 2'nin kodunuzu bizimkilerle karşılaştırabilmesini tercih ederiz.

Genel kurallar geçerlidir, en kısa bayt kazanır. Standart kod golf boşlukları geçerlidir. Artık komik olmayan standart "boşluklar"

İyi eğlenceler!


2
@Rainbolt: Tamam, herhangi bir dile izin verildi. Python sınırlaması karşılaştırma amaçlıdır. Ama ne istersen yap: D
sammko

3 ve 5092'den başka cevaplar var mı? 10.000.000'dan önce başka bir şey bulamıyorum.
kennytm

@KennyTM: 4 ve 5092 aldım. Ve evet, başkaları olduğunu sanmıyorum.
sammko

Hey, ne istediğini daha iyi yansıtmak için unvanını düzenledim. Bir şeyi özlediğimi düşünüyorsanız bunu değiştirmekten çekinmeyin.
FryAmTheEggman

Bu arada python etiketi kaldırıldı.
Timtech

Yanıtlar:


21

Mathematica, 8 bayt

{4,5092}

4 ve 5092'nin tek çözüm olduğunu kanıtlayın: Orijinal sorun şu şekilde yeniden yazılabilir:

x (x + 2010) = 2014 GCD (x, x + 2010) 2

Hadi yazma x 2 olarak bir 2 3 a 3 5 bir 5 ... ve x + 2010 2 olarak b 2 3 b 3 5 b 5 ... Sonra denklem haline gelir

2 a 2 + b 2 3 a 3 + b 3 5 a 5 + b 5 … = 2014 2 2dak (a 2 , b 2 ) 3 2dak (a 3 , b 3 ) 5 2dak (a 5 , b 5 )

2014 = 2 × 19 × 53 olduğundan,

a p + b p = 2dk (a p , b p ) + {eğer p ∈ {2, 19, 53}, 0 ise}

Böylece

a p = b p ise p ≠ 2, 19, 53
a p = b p ± 1 başka

Böylece

x + 2010 = 2 ± 1 19 ± 1 53 ± 1 x

Sadece 8 olası seçenek vardır ve 4 ve 5092'nin tek pozitif tamsayı çözümleri olup olmadığını kolayca kontrol edebiliriz.

Bekle, insanların standart boşluk çığlık attığını duyuyorum…

Mathematica, 45 bayt

Select[Range[9^7],2014GCD[#,s=#+2010]^2==s#&]

4

Pyth 27 25

J2010fq+J4/*T+TJ^iTJ2U^T6

Çevrimiçi deneyin.

Bu algoritmanızı oldukça naif kullanır ... Daha iyi bir şey bulabilirim ...

Temel olarak ölçütü karşılamayan değerleri filtreler range(10**6)

@Xnor'a sohbette dikkat çeken için teşekkürler gcd(x,x+2010)==gcd(x,2010)


3

Python 3, 84 bayt

FryAmTheEggman, 88 baytlık çözümünüzü nasıl yapacağınızı zaten önerdi, bu yüzden bunu göndermeyeceğim. Ama Python 3'te nasıl daha az bayt alabileceğinizi göstereceğimi düşündüm:

from fractions import*
x=10**6
while x:y=x+2010;x*y-gcd(x,y)**2*2014or print(x);x-=1

(İpuçları için FryAmTheEggman için teşekkürler)

Bu printbir işlev olmadığından Python 2'de çalışmaz.

İzin verdiğimizden emin değilim, ama 9**9bunun yerine kullanabilseydik 10**6başka bir bayt olurdu.


Bunu yapmanın bir yolu olduğunu biliyordum and/ or... python 3'ü düşünmezdi;) Konu hakkında daha fazla bilgi: Sipariş önemli değilse, ayar x=10**6ve yapmanın while x:x-=1;...bir bayt daha kısa olduğunu düşünüyorum .
FryAmTheEggman

@FryAmTheEggman Sorunun görünüşünden sipariş önemli görünmüyor, bu yüzden ben koyacağım. Teşekkürler!
Sp3000

2

R, 75 karakter

for(a in 1:1e6){q=1:a;b=a+2010;if(a*b/max(q[!a%%q&!b%%q])^2==2014)print(a)}

Satır kesmeleri ile:

for(a in 1:1e6){
    q=1:a
    b=a+2010
    if(a*b/max(q[!a%%q&!b%%q])^2==2014)print(a)
    }

2

GolfScript (41 bayt)

İki doğal sayının farkı 2010 ve en büyük ortak paydaları, en düşük ortak katlarından 2014 kat daha küçük. Olası tüm çözümleri bulun.

Numaraları amve bmnerede gcd(a, b) = 1ve wlog'u arayın b > a. O zaman fark m(b-a) = 2010, ve lcm(am, bm) = abm = 2014mböylece ab=2014.

2014'ün faktörleri

1 * 2014
2 * 1007
19 * 106
38 * 53

ve 2010'a bölünen farklılıkları olanlar

1007 - 2 => m = 2, solution is 4, 2014
53 - 38 => m = 134, solution is 5092, 7102

Yerleşik GCD veya LCM içermeyen bir dilde çalıştığım için, bu analiz muhtemelen programı kısaltmaktadır:

44,{).2014{.2$/\@%!}:,~\2$- 2010,***}%0-`

nerede 44olduğunu floor(sqrt(2014)).

Saf bir döngü kullanarak oldukça yakınlaşmak mümkündür:

10 6?,1>{.2010+.2${.@\%.}do;.*2014*@@*=},`

Peki @ KettyTM'in (4.55092) tek çözüm yanlış olduğuna dair kanıt?
Optimize Edici,

@Optimizer, yanlış okuyorsun. Ayrıca iki çözüm olduğunu kanıtlıyor ve bunlar benim çözümlerimle aynı. Kanıtını takip etmek benimkinden (IMAO) çok daha zor.
Peter Taylor

Ah, doğru. Ve evet, seninki ondan daha mantıklı.
Optimize Edici

2

Perl6 61 58 56 54 52

Kaynağınızın oldukça doğrudan bir çevirisi

for ^10**6 ->\i{i.say if i*(i+2010)/(i gcd(i+2010))**2==2014}

gcd Perl6'da bir infix op.

^10**6kısaltmasıdır 0 ..^ 10**6nerede, ^araç aralığından bu numarayı dahil değildir.


Tabii ki i gcd (i+2010)aynı i gcd 20103 karakter kaydedebilirim

for ^10**6 ->\i{i.say if i*(i+2010)/(i gcd 2010)**2==2014}

$_Bunun yerine kullanırsam ibaşka bir kaç karakter kaydedebilirim. ( .saykısaltmasıdır $_.say)

for ^10**6 {.say if $_*($_+2010)/($_ gcd 2010)**2==2014}

Bunun ... && .sayyerine kullanarak başka bir çift karakter kaydedebilirim .say if ..., çünkü benim için her iki tarafta da bir boşluğa ihtiyacım &&yok if.

for ^10**6 {$_*($_+2010)/($_ gcd 2010)**2==2014&&.say}

Önceki "optimizasyonların" her ikisini de yaptığımdan beri, deyim değiştirici formunu kullanabilirim for, yani kaldırabilir {ve }.

$_*($_+2010)/($_ gcd 2010)**2==2014&&.say for ^10**6

Farklı bir algoritma kullanmadan gidebildiğim kadar kısa olduğunu düşünüyorum.


2

J, 26 bayt

   I.((*.=+.*4--)2010+])i.1e6
4 5092

Lanet olası 2 bayt fiiller ... :)


1

Dyalog APL, 29 karakter

      a←⍳10        ⍝ the integers up to 10
      a
1 2 3 4 5 6 7 8 9 10
      2010+a       ⍝ corresponding integers at distance 2010
2011 2012 2013 2014 2015 2016 2017 2018 2019 2020
      a∨2010+a     ⍝ GCD-s between elements of a and 2010+a
1 2 3 2 5 6 1 2 3 10
      ⍝ All APL functions (e.g. + and ∨) are prefix-or-infix, right-associative,
      ⍝ and of the same precedence.
      a∧2010+a     ⍝ LCM-s
2011 2012 2013 4028 2015 2016 14119 8072 6057 2020
      ⍝ For which of them is the LCM 2014 times the GCD?
      (a∧2010+a)=2014×a∨2010+a
0 0 0 1 0 0 0 0 0 0
      ⍝ 0 means false, 1 means true
      ⍝ Filter the elements of "a" corresponding to the 1-s
      ((a∧2010+a)=2014×a∨2010+a) / a
4
      ⍝ Let's abstract this as a function by using curlies.
      ⍝ Omega (⍵) stands for the right argument.
      {((⍵∧2010+⍵)=2014×⍵∨2010+⍵) / ⍵} a
4
      ⍝ Up to a million instead of up to ten:
      {((⍵∧2010+⍵)=2014×⍵∨2010+⍵) / ⍵} ⍳1e6
4 5092
      ⍝ Hey, we can save a few characters by making 2010 the left argument, alpha (⍺)
      2010 {((⍵∧⍺+⍵)=2014×⍵∨⍺+⍵) / ⍵} ⍳1e6
4 5092
      ⍝ Remove a pair of parens by using the switch operator ⍨
      ⍝ An "operator" occurs to the right of a function and modifies its behaviour.
      ⍝ In this case A f⍨ B means the same as B f A
      ⍝ Left and right are swapped, hence "switch".
      2010 {⍵ /⍨ (⍵∧⍺+⍵)=2014×⍵∨⍺+⍵)} ⍳1e6
4 5092
      ⍝ That's 32 characters (modulo whitespace).  Not bad, but we can do better.
      ⍝ A "fork" is a sequence of 3 functions in isolation: f g h
      ⍝ It is evaluated as:  ⍺(f g h)⍵  ←→  (⍺ f ⍵)g(⍺ h ⍵)
      ⍝ If the first item is an array instead of a function: A f g  ←→  {A} f g
      ⍝ Forks are right-associative: f g h k l ←→ f g (h k l)
      2010 {⍵ /⍨ (⍺(⊢∧+)⍵)=2014×(⍺(⊢∨+)⍵)} ⍳1e6
4 5092
      ⍝ The "right tack" function (⊢) simply returns its right argument
      ⍝ Let's abuse forks a little further:
      2010 {⍵ /⍨ ⍺((⊢∧+)=(2014×(⊢∨+)))⍵} ⍳1e6
4 5092
      ⍝ ... and more
      2010 {⍺ (⊢(/⍨)((⊢∧+)=(2014×(⊢∨+)))) ⍵} ⍳1e6
4 5092
      ⍝ But {⍺ f ⍵} is equivalent to f
      2010 (⊢(/⍨)((⊢∧+)=(2014×(⊢∨+)))) ⍳1e6
4 5092
      ⍝ Note that now we are not mentioning ⍺ and ⍵ at all.
      ⍝ This is called "point-free style" or "tacit programming".
      ⍝ Removing some unnecessary parens and whitespace:
      2010(⊢(/⍨)(⊢∧+)=2014×⊢∨+)⍳1e6
4 5092
      ⍝ How many characters?
      ⍴'2010(⊢(/⍨)(⊢∧+)=2014×⊢∨+)⍳1e6'
29

1

PARI / GP, 42 bayt

[n|n<-[1..8!],2014*gcd(n,t=n+2010)^2==n*t]

GP'nin fordivyapısını kullanan son derece zarif bir çözüm olduğunu hissediyorum, ancak bu öz ile sırf kısalık için rekabet edemedi.


0

Raket, 72 karakter

(filter(λ(i)(=(/(*(+ i 2010)i)(expt(gcd(+ i 2010)i)2))2014))(range 1e6))

1
Racket ISO-8859-7 ile çalışır mı? Aksi takdirde λ1 bayt sayılmaz .
kennytm

0

Haskell, 52 karakter

show [x|x<-[1..6^8],x*(x+2010)==2014*(gcd x 2010)^2]

Haskell interaktif ortamında GHCi çalışır.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.