Kesik basamakların hesaplanması pi güçlerinin toplamı


12

Pozitif bir n tamsayısı verildiğinde , π n'nin kesirli kısmının ilk n ondalık basamağının toplamı .

Örnek giriş ve çıkışlar:

1 → 1
2 → 14
3 → 6
4 → 13
5 → 24
50 → 211
500 → 2305
5000 → 22852

Π rakamlarını hesaplayan veya güç serilerini veya sürekli kesirleri değerlendiren yerleşik işlevlere izin verilmez. Standart boşluklar geçerlidir. Giriş / çıkış uygun bir biçimde olabilir (stdin, stdout, giriş / çıkış işlevi, vb.).

Bayt cinsinden en kısa kod kazanır.


Pi hesaplamak için kullanılabilecek, ancak arktanjant veya hayali logaritmalar gibi doğrudan gerekli olmayan diğer trig fonksiyonları da yasaklanmış mı? Ayrıca, n'den sonra başarısız olabileceği bir üst sınır var mı?
FryAmTheEggman

@FryAmTheEggman Bu trig işlevleri pi'nin rasgele rakamlarını hesaplayabiliyorsa, evet yasaklanır. Programınız herhangi bir n için teoride çalışmalıdır , ancak çalışma zamanı veya bellek çok yükselirse affedilir.
orlp

Yanıtlar:


4

Python - 191 Bayt

t=i=1L;k=n=input();f=2000*20**n;A=range(n+1)
for k in range(2,n):A=[(A[j-1]+A[j+1])*j>>1for j in range(n-k+1)];f*=k
while k:k=(1-~i*n%4)*f/A[1]/i**n;t+=k;i+=2
print sum(map(int,`t`[-n-4:-4]))

~ 4x daha hızlı sürüm - 206 bayt

t=i=1L;k=n=input();f=2000*20**n;A=[0,1]+[0]*n
for k in range(1,n):
 f*=k
 for j in range(-~n/2-k+1):A[j]=j*A[j-1]+A[j+1]*(j+2-n%2)
while k:k=(1-~i*n%4)*f/A[1]/i**n;t+=k;i+=2
print sum(map(int,`t`[-n-4:-4]))

Giriş stdin'den alınır. N = 5000 çıktısı , ikinci komut dosyasıyla (veya birincisiyle 60 saniye) yaklaşık 14 saniye sürer.


Örnek kullanım:

$ echo 1 | python pi-trunc.py
1

$ echo 2 | python pi-trunc.py
14

$ echo 3 | python pi-trunc.py
6

$ echo 4 | python pi-trunc.py
13

$ echo 5 | python pi-trunc.py
24

$ echo 50 | python pi-trunc.py
211

$ echo 500 | python pi-trunc.py
2305

$ echo 5000 | python pi-trunc.py
22852

Kullanılan formül aşağıdaki gibidir:

burada A , n olup , n inci Alternatif Numarası resmi büyüklükte bir dizi alternatif permütasyon sayısı olarak tanımlanabilir, N (Ayrıca bkz: A000111 ). Alternatif olarak sekans Teğet Sayılar bileşimin ve Kiriş numaralar gibi tanımlanabilir ( bir 2n = S , n , A 2n + 1 = T , n ), daha sonra ayrıntılı bilgi.

Küçük düzeltme faktörü c n , n büyüdükçe hızla 1'e yakınlaşır ve şu şekilde verilir:

For n = 1 , değerlendirmek için bu miktarlar Leibniz Serisi . Π 10 ½ olarak yaklaşık olarak , gerekli terim sayısı şu şekilde hesaplanabilir:

daha küçük n değerleri önemli ölçüde daha fazlasını gerektirse de , bu değer 17'ye yaklaşır (yuvarlanır) .

A n'nin hesaplanması için birkaç algoritma ve hatta açık bir formül vardır, ancak hepsi n ile kuadratiktir . Başlangıçta Seidel'in Algoritmasının bir uygulamasını kodladım , ancak pratik olmak için çok yavaş görünüyor. Her yineleme ek bir terimin saklanmasını gerektirir ve terimler çok hızlı bir şekilde artar ("yanlış" tür O (n 2 ) ).

İlk komut dosyası, Knuth ve Buckholtz tarafından orijinal olarak verilen bir algoritmanın bir uygulamasını kullanır :

Tüm k = 1 için T 1, k = 1 olsun.

Müteakip T değerleri nüks ilişkisi ile verilir:

T n + 1, k = 1/2 [ (k - 1) T n, k-1 + (k + 1) T n, k + 1 ]

Bir n daha sonra T ile verilir n 1

(ayrıca bakınız: A185414 )

Açıkça belirtilmemesine rağmen, bu algoritma hem Teğet Sayıları hem de Sekant Numaralarını aynı anda hesaplar. İkinci senaryo, Brent ve Zimmermann tarafından bu algoritmanın n'nin paritesine bağlı olarak T veya S'yi hesaplayan bir varyasyonunu kullanır . İyileştirme n / 2 ile kuadratiktir , bu nedenle ~ 4x hız artışı.


1
Cevabınızın arkasındaki matematiğin mükemmel açıklaması.
Mantık Şövalyesi

3

Python 2, 246 bayt

İkinci dereceden yakınsama ile Calculate answer cevabım için benzer bir yaklaşım izledim . Son satır pi'nin N'inci gücünü alır ve rakamları toplar. N = 5000 testi bir dakika kadar sürer.

from decimal import*
d=Decimal
N=input()
getcontext().prec=2*N
j=d(1)
h=d(2)
f=h*h
g=j/h
a=j
b=j/h.sqrt()
t=j/f
p=j
for i in bin(N)[2:]:e=a;a,b=(a+b)/h,(a*b).sqrt();c=e-a;t-=c*c*p;p+=p
k=a+b
l=k*k/f/t
print sum(map(int,`l**N`.split('.')[1][:N]))

Bazı testler:

$ echo 1 | python soln.py
1
$ echo 3 | python soln.py
6
$ echo 5 | python soln.py
24
$ echo 500 | python soln.py
2305
$ echo 5000 | python soln.py
22852

Çözülmemiş kod:

from decimal import *
d = Decimal

N = input()
getcontext().prec = 2 * N

# constants:
one = d(1)
two = d(2)
four = two*two
half = one/two

# initialise:
a = one
b = one / two.sqrt()
t = one / four
p = one

for i in bin(N)[2:] :
    temp = a;
    a, b = (a+b)/two, (a*b).sqrt();
    pterm = temp-a;
    t -= pterm*pterm * p;
    p += p

ab = a+b
pi = ab*ab / four / t
print sum(map(int, `pi ** N`.split('.')[1][:N]))

Çizgi 8, sen açabilirsiniz a=jve p=jkarşı a=p=jiirc. Olabilir.
Elias Benevedes

Teşekkürler. Bu kod için daha fazla golf optimizasyonu var, ancak Decimal olmadan bir algoritma kullanarak yeniden yazma olmadan rekabetçi olmayacak.
Mantık Şövalyesi

1

Pyth, 33

s<>j^u+/*GHhyHy^TyQr*TQ0ZQT_y*QQQ

Bu cevaba göre isaacg . Muhtemelen daha fazla golf olabilir. Yavaş.

s<>j            Digit sum of...
  ^                 
    u               Evaluate pi = 2 + 1/3*(2 + 2/5*(2 + 3/7*(2 + 4/9*(2 + ...))))
      +
        /
          *GH
          hyH
        y^TyQ       Except we generate a large integer containing 2n digits,
                    rather than a fraction.
      r*TQ0         Experimentally verified that 10*n iterations will give enough
                    precision for 2n digits (# digits correct grows faster than 2n).
      Z
    Q               To the nth power.
  T_y*QQQ         Get the last 2n^2 digits (all the fractional digits) and get the
                  first n fractional digits.

1
Bu cevabın, doğru cevabı almak için yeterli rakamı hesapladığını gerekçelendirmek için gerçekten en az yeterli açıklamaya ihtiyacı vardır.
Peter Taylor

@PeterTaylor Yarın bir açıklama ekleyeceğim, hemen yatağa gitmek üzereyim.
orlp

Her yineleme bir doğru bit üretir (bkz. Ek A ). 2n basamak ~ 6.64n yineleme gerektirmelidir.
primo
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.