รวมตัวหาร Fibonaccified ของฉัน!


14

ลำดับ Fibonacci ที่มีชื่อเสียงคือF(0) = 0; F(1) = 1; F(N+1) = F(N) + F(N-1)(สำหรับความท้าทายนี้เราเริ่มต้นด้วย 0)

ความท้าทายของคุณ: ให้nการส่งออกรวมของทั้งหมดd TH ตัวเลข Fibonacci สำหรับหารทุกวันของn TH จำนวนฟีโบนักชี หากคุณต้องการสัญลักษณ์ที่เป็นทางการมากกว่านี้

ผลรวม

อินพุต : จำนวนเต็มบวกn

ผลลัพธ์ : ผลรวม

n=4ตัวอย่างเช่นพิจารณา F(4) = 3หาร 3 คือ 1 และ 3 F(1) + F(3) = 1 + 2 = 3เพื่อให้ผลผลิตที่ควรจะเป็น

สำหรับn=6, F(6) = 8และตัวหารของ 8 คือ 1, 2, 4, 8, F(1) + F(2) + F(4) + F(8) = 1 + 1 + 3 + 21 = 26เพื่อส่งออกเป็น

กรณีทดสอบ:

1 => 1
2 => 1
3 => 2
4 => 3
5 => 6
6 => 26

นี่คือคำตอบที่สั้นที่สุดในหน่วยไบต์ชนะ ช่องโหว่มาตรฐานใช้

คำตอบ:


2

ที่จริงแล้ว 5 ไบต์

F÷♂FΣ

ลองออนไลน์!

มันทำงานอย่างไร

       (implicit) Read n from STDIN.
F      Compute F(n).
 ÷     Get F(n)'s divisors.
  ♂F   Map F over the divisors.
    Σ  Take the sum.

ชื่อของภาษาทำให้ดูเหมือนก้าวร้าวก้าวร้าวนั่นตั้งใจหรือไม่?
Rohan Jhunjhunwala

1
ฉันสงสัยมัน. รุ่นแรกของภาษาที่เรียกว่าอย่างจริงจังเพราะความคิดเห็นนี้ สำหรับเวอร์ชั่นที่สองผู้เขียนเลือกใช้คำคุณศัพท์ต่อไป
Dennis

6

เยลลี่ขนาด 7 ไบต์

ÆḞÆDÆḞS

ลองออนไลน์!

คำอธิบาย:

ÆḞÆDÆḞS Main link (Arguments: z)
ÆḞ      zth Fibonacci number's
  ÆD                           divisors'
    ÆḞ                                   Fibonacci numbers'
      S                                                     sum

อุกอาจอย่างแน่นอน! ฉันไม่รู้ภาษาแปลกใหม่ใด ๆ แต่ดูเหมือนว่าฉันจะสามารถเขียนอัลกอริธึมทั้งหมดด้วยอักขระบางตัวได้
Bogdan Alexandru

@BogdanAlexandru คุณจะเห็นได้ว่าตัวบิวอินส่วนใหญ่ที่ใช้ในที่นี้ใช้ 2 ไบต์เนื่องจากไม่เหมาะกับ 1 ไบต์ ดูเดนนิสที่จริงคำตอบสำหรับตัวอักษรที่น้อยลง นอกจากนี้ Jelly ยังเป็น "ภาษาการเล่นกอล์ฟ" ซึ่งเป็นภาษาที่สร้างขึ้นสำหรับโค้ดกอล์ฟโดยเฉพาะและเป็นหนึ่งในภาษาที่มีประสิทธิภาพมากที่สุดที่นี่ (แม้ว่าจะไม่มีภาษา
Erik the Outgolfer

คุณกำลังบอกว่าภาษาเหล่านี้ไม่ได้ใช้ในทางปฏิบัติและมันมีไว้สำหรับความท้าทายเท่านั้น?
Bogdan Alexandru


4

Mathematica Simplifiedขนาด 14 ไบต์

Fi@#~Div9`~Fi&

โอ้มันเป็นสิ่งที่เหมือนกับโซลูชันของ @ MartinEnder ...


อืม ... ใช้ภาษาเดียวกันกับเวอร์ชั่นที่สั้นกว่า ... ฉันเดาว่าใช้งานได้
Neil A.

ไม่มีชื่อฟังก์ชันตัวอักษรเดี่ยวใน Mathematica ใช่ไหม? คุณไม่สามารถจับคู่สตริงอักขระทั้งสองตัวที่เกิดจากตัวอักษรตัวพิมพ์ใหญ่นำหน้ารวมกับไบต์เดียวได้หรือไม่ ถ้าเป็นเช่นนั้นคุณจะมีชื่อฟังก์ชั่น 2-byte ที่ง่าย 26 * 256 = 6656 เพียงพอสำหรับชื่อ 6356 11.1.1 ที่เหลือ 300
Jonathan Allan

@JanathanAllan ความคิดที่ดี (แต่มีฟังก์ชั่นชื่อเดียวเช่นN)
JungHwan Min


2

05AB1E , 11 ไบต์

!ÅFDI<èÑ<èO

ลองออนไลน์!

คำอธิบาย

!            # factorial of input
 ÅF          # get the list of fibonacci numbers (starting at 1)
             # smaller than or equal to this
   D         # duplicate list of fibonacci number
    I<è      # get the element at index (input-1)
       Ñ     # get the list of its divisors
        <    # decrement each
         è   # get the fibonacci numbers at those indices
          O  # sum


2

อลิซ , 38 36 ไบต์

ขอขอบคุณลีโอสำหรับการบันทึก 2 ไบต์

/ow;B1dt&w;31J
\i@/01dt,t&w.2,+k;d&+

ลองออนไลน์!

เกือบจะไม่เหมาะสมที่สุด ขั้นตอนการควบคุมนั้นค่อนข้างละเอียดและในขณะที่ฉันมีความสุขกับจำนวนไบต์ที่บันทึกไว้ในเวอร์ชันก่อนหน้านี้ฉันมีความรู้สึกว่าฉันเข้าใจสิ่งต่าง ๆ มากเกินไปซึ่งอาจเป็นวิธีที่ง่ายและสั้นกว่า

คำอธิบาย

ก่อนอื่นฉันต้องอธิบายอย่างละเอียดเกี่ยวกับที่อยู่ผู้ส่งคืนของอลิซ (RAS) เช่นเดียวกับ fungeoids อื่น ๆ อลิซมีคำสั่งให้กระโดดไปมาในโค้ด อย่างไรก็ตามมันยังมีคำสั่งให้กลับไปยังที่ที่คุณมาซึ่งช่วยให้คุณสามารถใช้รูทีนย่อยได้สะดวก แน่นอนว่านี่เป็นภาษา 2D รูทีนย่อยมีอยู่จริงโดยการประชุมเท่านั้น ไม่มีอะไรที่จะหยุดคุณไม่ให้เข้าหรือออกจากรูทีนย่อยผ่านวิธีการอื่นนอกเหนือจากคำสั่ง return (หรือ ณ จุดใด ๆ ในรูทีนย่อย) และขึ้นอยู่กับวิธีที่คุณใช้ RAS อาจไม่มีลำดับขั้น

โดยทั่วไปสิ่งนี้ถูกนำไปใช้โดยการให้คำสั่งข้ามjส่งที่อยู่ IP ปัจจุบันไปที่ RAS ก่อนที่จะกระโดด คำสั่ง return kจะปรากฏที่อยู่ของ RAS และข้ามไปที่นั่น ถ้า RAS ว่างเปล่าkไม่ทำอะไรเลย

นอกจากนี้ยังมีวิธีอื่นในการปรับแต่ง RAS สองสิ่งนี้เกี่ยวข้องกับโปรแกรมนี้:

  • wผลักที่อยู่ IP ปัจจุบันไปที่ RAS โดยไม่ต้องกระโดดไปทุกที่ ถ้าคุณทำซ้ำคำสั่งนี้คุณสามารถเขียนลูปง่าย ๆ ได้อย่างสะดวก&w...kซึ่งฉันได้ทำไปแล้วในคำตอบที่ผ่านมา
  • Jเป็นเหมือนjแต่จำไม่ได้ว่าที่อยู่ IP ปัจจุบันบน RAS

สิ่งสำคัญคือต้องทราบว่า RAS เก็บข้อมูลเกี่ยวกับทิศทางของ IP ดังนั้นการกลับไปยังที่อยู่ด้วยkจะเป็นการรักษาทิศทาง IP ปัจจุบันเสมอ(และดังนั้นไม่ว่าเราจะอยู่ในโหมด Cardinal หรือ Ordinal) โดยไม่คำนึงถึงวิธีที่เราส่งผ่านjหรือwผลัก IP แอดเดรสในครั้งแรก

ด้วยวิธีการดังกล่าวเริ่มต้นด้วยการดูในรูทีนย่อยในโปรแกรมด้านบน:

01dt,t&w.2,+k

รูทีนย่อยนี้ดึงองค์ประกอบด้านล่างของสแต็กnไปยังด้านบนแล้วคำนวณตัวเลขฟีโบนักชีF (n)และF (n + 1) (ทิ้งไว้ที่ด้านบนของสแต็ก) เราไม่จำเป็นต้องใช้F (n + 1)แต่มันจะถูกทิ้งนอกรูทีนย่อยเนื่องจาก&w...kลูปโต้ตอบกับ RAS อย่างไร (ซึ่งลูปเหล่านี้ต้องการลูปเหล่านี้ในตอนท้ายของรูทีนย่อย) เหตุผลที่เรารับองค์ประกอบจากด้านล่างแทนด้านบนคือสิ่งนี้ช่วยให้เราปฏิบัติกับสแต็คได้มากกว่าซึ่งหมายความว่าเราสามารถคำนวณหมายเลขฟีโบนักชีทั้งหมดได้ในครั้งเดียวโดยไม่ต้องเก็บไว้ที่อื่น

นี่คือการทำงานของรูทีนย่อยนี้:

                                                          Stack
01    Push 0 and 1, to initialise Fibonacci sequence.     [n ... 0 1]
dt,   Pull bottom element n to top.                       [... 0 1 n]
t&w   Run this loop n times...                            [... F(i-2) F(i-1)]

  .     Duplicate F(i-1).                                 [... F(i-2) F(i-1) F(i-1)]
  2,    Pull up F(i-2).                                   [... F(i-1) F(i-1) F(i-2)]
  +     Add them together to get F(i).                    [... F(i-1) F(i)]

k     End of loop.

จุดสิ้นสุดของลูปนั้นค่อนข้างยุ่งยาก ตราบใดที่มีสำเนาของที่อยู่ 'w' ในสแต็กนี่จะเริ่มต้นการทำซ้ำครั้งถัดไป เมื่อสิ่งเหล่านั้นหมดลงผลลัพธ์ขึ้นอยู่กับวิธีการเรียกรูทีนย่อย หากเรียกรูทีนย่อยด้วย 'j' 'k' สุดท้ายจะส่งคืนที่นั่นดังนั้นลูปสิ้นสุดจะเพิ่มขึ้นเป็นสองเท่าเมื่อรูทีนย่อยกลับมา หากรูทีนย่อยถูกเรียกด้วย 'J' และยังคงมีที่อยู่จากสแต็กก่อนหน้าเราจะกระโดดไปที่นั่น นี่หมายความว่าหากเรียกรูทีนย่อยในลูปภายนอกตัวเอง 'k' นี้จะกลับไปที่จุดเริ่มต้นของลูปภายนอก หากรูทีนย่อยนั้นถูกเรียกด้วย 'J' แต่ RAS ว่างเปล่าในขณะนี้ 'k' นี้จะไม่ทำอะไรเลยและ IP ก็จะเคลื่อนที่ไปเรื่อย ๆ หลังจากวนรอบ เราจะใช้ทั้งสามกรณีนี้ในโปรแกรม

ในที่สุดเมื่อไปถึงโปรแกรมของตัวเอง

/o....
\i@...

สิ่งเหล่านี้เป็นเพียงการแนะนำสั้น ๆ สองอย่างในโหมด Ordinal เพื่ออ่านและพิมพ์เลขจำนวนเต็มฐานสิบ

หลังจากที่iมีการwซึ่งจำตำแหน่งปัจจุบันก่อนที่จะผ่านเข้าไปใน subroutine /เนื่องจากสอง นี้ภาวนาแรกของ subroutine คำนวณF(n)และในการป้อนข้อมูลF(n+1) nหลังจากนั้นเราก็กระโดดกลับมาที่นี่ แต่ตอนนี้เรากำลังเคลื่อนไปทางตะวันออกดังนั้นส่วนที่เหลือของผู้ให้บริการโปรแกรมในโหมด Cardinal โปรแกรมหลักมีลักษณะดังนี้:

;B1dt&w;31J;d&+
        ^^^

นี่31Jคือการเรียกรูทีนย่อยอื่นและดังนั้นจึงคำนวณจำนวนฟีโบนักชี

                                              Stack
                                              [F(n) F(n+1)]
;     Discard F(n+1).                         [F(n)]
B     Push all divisors of F(n).              [d_1 d_2 ... d_p]
1     Push 1. This value is arbitrary.        [d_1 d_2 ... d_p 1]
      The reason we need it is due to
      the fact that we don't want to run
      any code after our nested loops, so
      the upcoming outer loop over all
      divisors will *start* with ';' to
      discard F(d+1). But on the first
      iteration we haven't called the
      subroutine yet, so we need some 
      dummy value we can discard.
dt&w  Run this loop once for each element     [d_1 d_2 ... d_p 1]
      in the stack. Note that this is once    OR
      more than we have divisors. But since   [d_i d_(i+1) ... F(d_(i-1)) F(d_(i-1)+1)] 
      we're treating the stack as a queue,
      the last iteration will process the 
      first divisor for a second time. 
      Luckily, the first divisor is always 
      1 and F(1) = 1, so it doesn't matter 
      how often we process this one.

  ;     Discard the dummy value on the        [d_1 d_2 ... d_p]
        first iteration and F(d+1) of         OR
        the previous divisor on subsequent    [d_i d_(i+1) ... F(d_(i-1))]
        iterations.
  31J   Call the subroutine without pushing   [d_(i+1) ... F(d_i) F(d_i+1)]
        the current address on the RAS.
        Thereby, this doubles as our outer
        loop end. As long as there's an
        address left from the 'w', the end
        of the subroutine will jump there
        and start another iteration for the
        next divisor. Once that's done, the
        'k' at the end of the subroutine will
        simply do nothing and we'll continue
        after it.

;     Discard the final F(d_i+1).
d&+   Get the stack depth D and add the top   [final result]
      D+2 values. Of course that's two more
      than we have divisors, but the stack is
      implicitly padded with zeros, so that
      doesn't matter.

1

ความจริง 68 ​​ไบต์

g==>fibonacci;f(x:NNI):NNI==(x<3=>1;reduce(+,map(g,divisors(g(x)))))

การทดสอบบางอย่าง

(46) -> [[i,f(i)] for i in [0,1,2,3,4,5,6,10,15] ]
   (46)
   [[0,1], [1,1], [2,1], [3,2], [4,3], [5,6], [6,26], [10,139583862540],
     [15,
      135823697912782666169062844948067355657769395021071830756126284114988028_
       12823029319917411196081011510136735503204397274473084444
     ]
   ]
                                       Type: List List NonNegativeInteger



1

R, 77 ไบต์

F=gmp::fibnum;N=F(scan());i=n=N-N;while(i<N)if(N%%(i=i+1)<1)n=n+F(i);print(n)

ใช้ประโยชน์จากไลบรารี 'gmp' มันมีฟังก์ชั่นฟีโบนัชชีในตัวและให้ความสามารถในการทำจำนวนมาก มันทำให้เกิดปัญหาเล็กน้อยกับ seqs และการใช้งานแม้ว่ามันจะยังเล็กกว่าการสร้างฟังก์ชั่น Fibonacci ของฉันเอง

คำอธิบาย

F=gmp::fibnum;               # Set F as fibnum function
N=F(scan());                 # get input and set N to the fibonacci number of that index
i=n=N-N;                     # set i and n to 0 with data type bigz
while(i<N)                   # loop while i < N
   if(N%%(i=i+1)<1)          # if incremented i is divisor of N 
       n=n+F(i);             # add F(i) to rolling sum
print(n)                     # output final result

ทดสอบ

> F=gmp::fibnum;N=F(scan());i=n=N-N;while(i<N)if(N%%(i=i+1)<1)n=n+F(i);print(n)
1: 6
2: 
Read 1 item
Big Integer ('bigz') :
[1] 26
> F=gmp::fibnum;N=F(scan());i=n=N-N;while(i<N)if(N%%(i=i+1)<1)n=n+F(i);print(n)
1: 10
2: 
Read 1 item
Big Integer ('bigz') :
[1] 139583862540
> F=gmp::fibnum;N=F(scan());i=n=N-N;while(i<N)if(N%%(i=i+1)<1)n=n+F(i);print(n)
1: 15
2: 
Read 1 item
Big Integer ('bigz') :
[1] 13582369791278266616906284494806735565776939502107183075612628411498802812823029319917411196081011510136735503204397274473084444

โดยไม่ใช้ gmp

81 ไบต์ , ฟังก์ชั่นวนซ้ำที่ช้าอย่างสิ้นหวังเมื่อเลือกหมายเลขใหญ่ (9+)

F=function(n)`if`(n<2,n,F(n-1)+F(n-2));sum(sapply(which((N=F(scan()))%%1:N<1),F))

88 ไบต์สูตรของ Binet ที่ทำงานได้ดีพอสมควรกับจำนวนที่มากขึ้น แต่ก็ยังมีค่า จำกัด จำนวนเต็มค่อนข้างเร็ว

F=function(n)round(((5+5^.5)/10)*((1+5^.5)/2)^(n-1));sum(F(which(F(N<-scan())%%1:N<1)))


0

CJam , 26 ไบต์

qi_[XY@{_2$+}*]_@\f%:!.*:+

ลองออนไลน์!

ฉันแน่ใจว่ามันสามารถทำได้ดีกว่า คำอธิบาย:

แนวคิดคือมีอาร์เรย์ของหมายเลข Fibonacci และ dot product โดยมีอาร์เรย์ที่มี 1 และ 0 หากจำนวนนั้นเป็นหรือไม่ใช่ตัวหารของอินพุต

qi                                 Read the input (n)
   [XY        ]                    Array starting with [1,2,...]
  _   @{_2$+}*                     Append n times the sum of the previous two
               _                   Duplicate the array
                @\f%               Modulo each item with n (0 if divisor, a number otherwise)
                    :!             Logical NOT everything (1 if divisor, 0 otherwise) 
                      .*:+         Dot product those two arrays


0

JavaScript (ES6), 105 104 103 101 97 ไบต์

i=>[...Array((g=(n,x=0,y=1)=>n--?g(n,y,x+y):x)(i)+1)].map((_,y)=>s+=g((z=g(i)/y)%1?0:z|0),s=0)&&s

ลองมัน

f=
i=>[...Array((g=(n,x=0,y=1)=>n--?g(n,y,x+y):x)(i)+1)].map((_,y)=>s+=g((z=g(i)/y)%1?0:z|0),s=0)&&s
o.innerText=f(j.value=4)
oninput=_=>o.innerText=f(+j.value)
<input id=j type=number><pre id=o>


ฉันคิดว่าคุณสามารถเปลี่ยน(z=g(i)/y)>~~zเป็น(z=g(i)/y)%1ถ้าคุณแค่ตรวจสอบว่าzเป็นจำนวนเต็ม
ETHproductions

@ETHproductions ที่สร้างโอเวอร์โฟลว์ที่สามารถแก้ไขได้โดยเปลี่ยนg(z)เป็นg(z|0)แต่ทำให้เรากลับมาเป็นจำนวนไบต์เดียวกัน
Shaggy



โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.