ความซับซ้อนในการคำนวณของลำดับฟีโบนักชี


330

ฉันเข้าใจสัญกรณ์ Big-O แต่ฉันไม่รู้วิธีคำนวณสำหรับฟังก์ชั่นมากมาย โดยเฉพาะฉันได้พยายามหาความซับซ้อนในการคำนวณของลำดับ Fibonacci รุ่นไร้เดียงสา:

int Fibonacci(int n)
{
    if (n <= 1)
        return n;
    else
        return Fibonacci(n - 1) + Fibonacci(n - 2);
}

ความซับซ้อนในการคำนวณของลำดับฟีโบนักชีคืออะไรและคำนวณอย่างไร?



3
ดูในส่วนรูปแบบเมทริกซ์ที่นี่: en.wikipedia.org/wiki/Fibonacci_number ด้วยการทำเมทริกซ์นี้ ^ n (ในวิธีที่ฉลาด) คุณสามารถคำนวณ Fib (n) ใน O (lg n) เคล็ดลับในการทำฟังก์ชั่นพลังงาน มีการบรรยายที่ดีมากใน iTunesU เกี่ยวกับปัญหานี้และวิธีการแก้ไขใน O (lg n) หลักสูตรนี้เป็นคำแนะนำเกี่ยวกับอัลกอริทึมจาก MIT lecture 3 (ซึ่งฟรีแน่นอนเพื่อตรวจสอบว่าคุณสนใจ)
Aly

1
ความคิดเห็นข้างต้นไม่ได้ตอบคำถามซึ่งเกี่ยวกับความซับซ้อนในการคำนวณของรุ่นที่ไร้เดียงสา (ในรหัสที่โพสต์) ไม่เกี่ยวกับรุ่นที่ฉลาดกว่าเช่นรูปแบบเมทริกซ์หรือการคำนวณแบบไม่เรียกซ้ำ
Josh Milthorpe

วิดีโอที่ดีมากที่นี่ซึ่งพูดถึงความซับซ้อนของขอบเขตล่าง (2 ^ n / 2) และความซับซ้อนขอบเขตบน (2 ^ n) ของการใช้แบบเรียกซ้ำ
RBT

1
ข้อความค้นหาด้านข้าง: การใช้งานฟีโบนัชชีซีรีส์ที่ไร้เดียงสาควรทำซ้ำหรือเรียกซ้ำ ?
RBT

คำตอบ:


374

คุณจำลองฟังก์ชันเวลาเพื่อคำนวณFib(n)เป็นผลรวมของเวลาในการคำนวณFib(n-1)บวกเวลาที่จะคำนวณFib(n-2)บวกเวลาที่รวมเข้าด้วยกัน ( O(1)) นี่คือการสันนิษฐานว่าการประเมินซ้ำของเดิมFib(n)ใช้เวลาเดียวกัน - นั่นคือไม่มีการบันทึกช่วยจำ

T(n<=1) = O(1)

T(n) = T(n-1) + T(n-2) + O(1)

คุณแก้ปัญหาความสัมพันธ์ซ้ำ (โดยใช้ฟังก์ชันสร้าง) และคุณจะได้คำตอบ

หรือคุณสามารถวาดต้นไม้ recursion ซึ่งจะมีความลึกnและสังหรณ์ใจคิดออกว่าฟังก์ชั่นนี้เป็น asymptotically จากนั้นคุณสามารถพิสูจน์การคาดเดาของคุณโดยการเหนี่ยวนำO(2n)

ฐาน: n = 1ชัดเจน

สมมติ, ดังนั้นT(n-1) = O(2n-1)

T(n) = T(n-1) + T(n-2) + O(1) ซึ่งเท่ากับ

T(n) = O(2n-1) + O(2n-2) + O(1) = O(2n)

อย่างไรก็ตามตามที่ระบุไว้ในความคิดเห็นนี่ไม่ใช่ขอบเขตที่แคบ ความจริงที่น่าสนใจเกี่ยวกับฟังก์ชั่นนี้คือ T (n) นั้นมีความเหมือนกับ asymptotically ตามตัวอักษรFib(n)เนื่องจากทั้งคู่ถูกกำหนดเป็น

f(n) = f(n-1) + f(n-2).

ใบไม้ของต้นไม้ที่เรียกซ้ำจะกลับมาเสมอ 1 ค่าของFib(n)คือผลรวมของค่าทั้งหมดที่ส่งคืนโดยใบในต้นไม้ที่เรียกซ้ำซึ่งเท่ากับจำนวนของใบ เนื่องจากแต่ละใบจะใช้เวลา O (1) เพื่อคำนวณเท่ากับT(n) Fib(n) x O(1)ดังนั้นข้อ จำกัด สำหรับฟังก์ชันนี้คือลำดับฟีโบนักชี (~ ) คุณสามารถค้นหาขอบเขตที่แน่นหนานี้โดยใช้ฟังก์ชันสร้างตามที่ฉันได้กล่าวไว้ข้างต้นθ(1.6n)


29
พิสูจน์ด้วยการเหนี่ยวนำ ดี +1
Andrew Rollings

แม้ว่าข้อ จำกัด จะไม่แน่น
กัปตันเซกฟอลท์

@Captain Segfault: ใช่ ฉันชี้แจงคำตอบ คุณจะได้รับขอบเขตที่แน่นโดยใช้วิธีการ GF ตามที่ฉันได้เขียนไว้ข้างต้น
Mehrdad Afshari

ใช้ StackOverflowException ของคุณเป็นเรื่องตลก เวลาเอ็กซ์โพเนนเชียลสามารถรับรู้ได้ง่ายด้วยค่าที่ค่อนข้างเล็กสำหรับ n
David Rodríguez - dribeas

1
"อีกวิธีหนึ่งคือคุณสามารถวาดทรีเรียกซ้ำซึ่งจะมีความลึก n และหาได้โดยสังหรณ์ว่าฟังก์ชั่นนี้เป็น asymptotically O (2n)" - สิ่งนี้เป็นเท็จอย่างสมบูรณ์ ความซับซ้อนของเวลาคือ O (golden_ratio ^ n) มันไม่เคยเข้าใกล้ O (2 ^ n) หากคุณสามารถเอื้อมมือไปหาอินฟินิตี้มันจะเข้าใกล้ O (golden_ratio ^ n) นั่นคือสิ่งที่เส้นกำกับคือระยะห่างระหว่างสองบรรทัดต้องเข้าหา 0
bob

133

เพียงแค่ถามตัวเองว่าจำเป็นต้องมีคำสั่งกี่ใบเพื่อF(n)ให้สมบูรณ์

สำหรับF(1)คำตอบคือ1(ส่วนแรกของเงื่อนไข)

สำหรับคำตอบคือF(n)F(n-1) + F(n-2)

ดังนั้นฟังก์ชั่นที่ตรงตามกฎเหล่านี้คืออะไร? ลองใช้n (a> 1):

a n == a (n-1) + a (n-2)

หารด้วย a (n-2) :

a 2 == a + 1

แก้หา aและคุณได้รับ(1+sqrt(5))/2 = 1.6180339887เป็นที่รู้จักกันเป็นอย่างอื่นเป็นอัตราส่วนทองคำ

ดังนั้นจึงต้องใช้เวลาชี้แจง


8
พิสูจน์โดยอุปนัย ดี +1
Andrew Rollings

2
30 upvotes สำหรับคำตอบที่ผิด? :-) มันเป็นไปตามที่ 1 = F (1) = (1 + sqrt (5)) / 2 หรือไม่ แล้วโซลูชันอื่นอีก (1-sqrt (5)) / 2
Carsten S

1
ไม่ 1 ไม่เท่ากับ 1 + 1 ฟังก์ชั่นที่ตอบสนองกฎเหล่านั้นได้ถูกกล่าวถึงในคำถาม
molbdnilo

6
คำตอบนั้นไม่ผิด มันไม่มีอาการ โซลูชันอื่น ๆ เป็นลบดังนั้นจึงไม่สมเหตุสมผล
Da Teng

10
ใครสามารถอธิบายได้ว่า ^ n == a ^ (n-1) + a ^ (n-2) เป็นไปตามกฎเหล่านี้อย่างไร เป็นที่น่าพอใจเพียงใดโปรดระบุให้ชัดเจน
ตรงไปตรงมา

33

ฉันเห็นด้วยกับ pgaur และ rickerbh ความซับซ้อนของ recursive-fibonacci คือ O (2 ^ n)

ฉันมาถึงข้อสรุปเดียวกันโดยค่อนข้างง่าย แต่ฉันเชื่อว่ายังคงใช้เหตุผลที่ถูกต้อง

อย่างแรกคือทั้งหมดที่เกี่ยวกับการหาจำนวนฟังก์ชัน fibonacci แบบเรียกซ้ำ (F () จากนี้เป็นต้นไป) จะถูกเรียกใช้เมื่อคำนวณจำนวน fibonacci Nth ถ้ามันถูกเรียกหนึ่งครั้งต่อหมายเลขในลำดับ 0 ถึง n ดังนั้นเรามี O (n) ถ้ามันถูกเรียก n ครั้งสำหรับแต่ละหมายเลขจากนั้นเราจะได้ O (n * n) หรือ O (n ^ 2) และอื่น ๆ

ดังนั้นเมื่อ F () ถูกเรียกสำหรับหมายเลข n จำนวนครั้งที่ F () ถูกเรียกสำหรับหมายเลขที่กำหนดระหว่าง 0 ถึง n-1 จะเพิ่มขึ้นเมื่อเราเข้าใกล้ 0

สำหรับความประทับใจครั้งแรกดูเหมือนว่าถ้าเราวางไว้ในลักษณะที่มองเห็นการวาดหน่วยต่อเวลา F () เรียกว่าตามจำนวนที่กำหนดเปียกให้ได้รูปทรงปิรามิด (นั่นคือถ้าเราตั้งหน่วยตามแนวนอน) ) บางสิ่งเช่นนี้

n              *
n-1            **
n-2           ****  
...
2           ***********
1       ******************
0    ***************************

ตอนนี้คำถามคือฐานของปิรามิดที่ขยายตัวเร็วแค่ไหนเมื่อ n เติบโตขึ้น?

ลองพิจารณากรณีจริงเช่น F (6)

F(6)                 *  <-- only once
F(5)                 *  <-- only once too
F(4)                 ** 
F(3)                ****
F(2)              ********
F(1)          ****************           <-- 16
F(0)  ********************************    <-- 32

เราเห็นว่า F (0) ได้รับการเรียก 32 ครั้งซึ่งเป็น 2 ^ 5 ซึ่งสำหรับกรณีตัวอย่างนี้คือ 2 ^ (n-1)

ตอนนี้เราต้องการทราบจำนวนครั้งที่ได้รับการเรียก F (x) และเราสามารถเห็นจำนวนครั้งที่การเรียก F (0) เป็นเพียงส่วนหนึ่งของสิ่งนั้น

หากเราย้ายเส้นของ * จากเส้น F (6) ไปยัง F (2) ลงในเส้น F (1) ทั้งหมดเราจะเห็นว่าเส้น F (1) และ F (0) มีความยาวเท่ากัน ซึ่งหมายความว่าจำนวนครั้งทั้งหมด F () จะถูกเรียกเมื่อ n = 6 คือ 2x32 = 64 = 2 ^ 6

ตอนนี้ในแง่ของความซับซ้อน:

O( F(6) ) = O(2^6)
O( F(n) ) = O(2^n)

3
F (3) ถูกเรียก 3 ครั้งเท่านั้นและไม่ 4 ครั้ง ปิรามิดที่สองผิด
Avik

2
F (3) = 3, F (2) = 5, F (1) = 8, F (0) = 5. ฉันจะแก้ไข แต่ฉันไม่คิดว่าฉันจะสามารถกู้คำตอบนี้ได้ด้วยการแก้ไข
Bernhard Barker

31

มีการอภิปรายที่ดีมากเรื่องนี้เป็นปัญหาที่เกิดขึ้นเฉพาะในช่วงที่เอ็มไอที บนหน้า 5 พวกเขาทำให้จุดที่ถ้าคุณคิดว่าการเพิ่มต้องใช้หน่วยคำนวณหนึ่งเวลาที่ต้องใช้ในการคำนวณ Fib (N) เกี่ยวข้องอย่างใกล้ชิดกับผลลัพธ์ของ Fib (N)

เป็นผลให้คุณสามารถข้ามโดยตรงไปยังการประมาณที่ใกล้เคียงที่สุดของชุด Fibonacci:

Fib(N) = (1/sqrt(5)) * 1.618^(N+1) (approximately)

และพูดว่าดังนั้นกรณีที่เลวร้ายที่สุดของขั้นตอนวิธีไร้เดียงสาคือ

O((1/sqrt(5)) * 1.618^(N+1)) = O(1.618^(N+1))

PS: มีการอภิปรายเกี่ยวกับการแสดงออกของตัวเลข Nth Fibonacciที่ปิดใน Wikipedia หากคุณต้องการข้อมูลเพิ่มเติม


ขอบคุณสำหรับลิงค์หลักสูตร การสังเกตการณ์ที่ดีมากเช่นกัน
SwimBikeRun

16

คุณสามารถขยายได้และมีการกระตุ้น

     T(n) = T(n-1) + T(n-2) <
     T(n-1) + T(n-1) 

     = 2*T(n-1)   
     = 2*2*T(n-2)
     = 2*2*2*T(n-3)
     ....
     = 2^i*T(n-i)
     ...
     ==> O(2^n)

1
ฉันเข้าใจบรรทัดแรก แต่ทำไมตอนนี้ถึงมีตัวละครน้อยกว่า<? คุณได้T(n-1) + T(n-1)อย่างไร
Quazi Irfan

@QuaziIrfan: D นั่นคือลูกศร -> [(ไม่น้อยกว่า) ขออภัยในความสับสนเกี่ยวกับบรรทัดสุดท้าย] สำหรับบรรทัดแรกอืม ... T(n-1) > T(n-2)ฉันสามารถเปลี่ยนT(n-2)และวางT(n-1)ได้ ฉันจะได้รับขอบเขตที่สูงขึ้นซึ่งยังคงใช้งานได้T(n-1) + T(n-2)
Tony Tannous

10

มันถูกผูกไว้ที่ปลายด้านล่างโดย2^(n/2)และบนปลายโดย 2 ^ n (ตามที่ระบุไว้ในความคิดเห็นอื่น ๆ ) และข้อเท็จจริงที่น่าสนใจของการใช้แบบเรียกซ้ำนั้นก็คือมันมีขอบเขตแบบ asymptotic ที่แน่นของ Fib (n) ข้อเท็จจริงเหล่านี้สามารถสรุปได้:

T(n) = Ω(2^(n/2))  (lower bound)
T(n) = O(2^n)   (upper bound)
T(n) = Θ(Fib(n)) (tight bound)

ขอบเขตที่ จำกัด สามารถลดลงได้อีกโดยใช้แบบฟอร์มปิดหากต้องการ


10

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

IN | OUT | TOT | LEAF | INT
 1 |   1 |   1 |   1  |   0
 2 |   1 |   1 |   1  |   0
 3 |   2 |   3 |   2  |   1
 4 |   3 |   5 |   3  |   2
 5 |   5 |   9 |   5  |   4
 6 |   8 |  15 |   8  |   7
 7 |  13 |  25 |  13  |  12
 8 |  21 |  41 |  21  |  20
 9 |  34 |  67 |  34  |  33
10 |  55 | 109 |  55  |  54

fib(n)อะไรทันทีกระโดดออกมาก็คือจำนวนโหนดใบ สิ่งที่ต้องทำซ้ำอีกสองสามอย่างที่ต้องสังเกตคือจำนวนโหนดภายในคือfib(n) - 1อะไรเอาซ้ำอีกไม่กี่ที่จะแจ้งให้ทราบก็คือว่าจำนวนโหนดภายในคือ2 * fib(n) - 1ดังนั้นจำนวนของโหนดคือ

θ(fib(n))ตั้งแต่คุณวางสัมประสิทธิ์จำแนกซับซ้อนในการคำนวณคำตอบสุดท้ายคือ


(ไม่ฉันไม่ได้วาดทรีโทรลึก 10 เต็มบนไวท์บอร์ดของฉันแค่ 5-deep.);)
benkc

นีซฉันสงสัยว่ามีส่วนเสริมเพิ่มเติมซ้ำอีกเท่าใดที่ Fib ทำซ้ำ มันไม่เพียงแค่เพิ่มเวลาการ1สะสมFib(n)ครั้งเดียวแต่น่าสนใจที่มันยังคงเหมือนθ(Fib(n))เดิม
Peter Cordes

โปรดทราบว่าบางคน (ส่วนใหญ่) การใช้งาน recursive ใช้เวลาเพิ่ม0แม้ว่า: กรณีฐาน recursion มี0และเพราะพวกเขาทำ1 Fib(n-1) + Fib(n-2)ดังนั้นอาจจะเป็น3 * Fib(n) - 2จากคำตอบของการเชื่อมโยงเพียงแค่นี้2 * Fib(n) - 1มีความถูกต้องมากขึ้นสำหรับจำนวนของโหนดไม่
Peter Cordes

ฉันไม่สามารถรับผลลัพธ์เดียวกันบนโหนดใบไม้ เริ่มต้นจาก 0: F (0) -> 1 leaf (ตัวมันเอง); F (1) -> 1 ใบ (ตัวมันเอง); F (2) -> 2 leafs (F (1) และ F (0)); F (3) -> 3 leafs; F (5) -> 8 แผ่น; ฯลฯ
alexlomba87

9

ความซับซ้อนของเวลาแบบอัลกอริทึมแบบเรียกซ้ำสามารถประมาณได้ดีขึ้นโดยการวาดแผนผังแบบเรียกซ้ำในกรณีนี้ความสัมพันธ์ที่เกิดซ้ำสำหรับการวาดแผนผังแบบเรียกซ้ำจะเป็น T (n) = T (n-1) + T (n-2) + O (1) แต่ละขั้นตอนใช้เวลา O (1) หมายถึงเวลาคงที่เนื่องจากจะทำการเปรียบเทียบเพียงครั้งเดียวเพื่อตรวจสอบค่าของ n ในถ้าบล็อกต้นไม้การเรียกคืนจะดูเหมือน

          n
   (n-1)      (n-2)
(n-2)(n-3) (n-3)(n-4) ...so on

ทีนี้สมมติว่าต้นไม้แต่ละต้นขึ้นไปแทนด้วย i ดังนั้น

i
0                        n
1            (n-1)                 (n-2)
2        (n-2)    (n-3)      (n-3)     (n-4)
3   (n-3)(n-4) (n-4)(n-5) (n-4)(n-5) (n-5)(n-6)

สมมติว่ามีค่าเฉพาะของ i, ต้นไม้จบลง, กรณีนั้นจะเป็นเมื่อ ni = 1, ดังนั้น i = n-1, หมายความว่าความสูงของต้นไม้คือ n-1 ทีนี้ลองมาดูกันว่ามีการทำงานมากน้อยเพียงใดสำหรับ n เลเยอร์ในต้นไม้โปรดทราบว่าแต่ละขั้นตอนใช้เวลา O (1) เวลาตามที่ระบุไว้ในความสัมพันธ์ที่เกิดซ้ำ

2^0=1                        n
2^1=2            (n-1)                 (n-2)
2^2=4        (n-2)    (n-3)      (n-3)     (n-4)
2^3=8   (n-3)(n-4) (n-4)(n-5) (n-4)(n-5) (n-5)(n-6)    ..so on
2^i for ith level

เนื่องจาก i = n-1 คือความสูงของงานต้นไม้ที่ทำในแต่ละระดับจะเป็น

i work
1 2^1
2 2^2
3 2^3..so on

ดังนั้นงานที่ทำทั้งหมดจะรวมผลงานที่ทำในแต่ละระดับดังนั้นมันจะเป็น 2 ^ 0 + 2 ^ 1 + 2 ^ 2 + 2 ^ 3 ... + 2 ^ (n-1) ตั้งแต่ i = n-1 โดยชุดเรขาคณิตผลรวมนี้คือ 2 ^ n ดังนั้นความซับซ้อนของเวลาทั้งหมดที่นี่คือO (2 ^ n)


2

ตามที่ฉันพูดถึงมันO(2^n)ในฟังก์ชั่นนี้การเรียกซ้ำเพียงอย่างเดียวก็ใช้เวลาพอสมควร เราจะเห็นว่าฟังก์ชั่นดังกล่าวจะยังคงอยู่ในต้นไม้จนใบมีวิธีเมื่อเราไปถึงระดับคือF(n-(n-1)) F(1)ดังนั้นที่นี่เมื่อเราจดความซับซ้อนของเวลาที่พบในแต่ละความลึกของต้นไม้ชุดสรุปคือ:

1+2+4+.......(n-1)
= 1((2^n)-1)/(2-1)
=2^n -1

2^n [ O(2^n) ]ที่เป็นคำสั่งของ


1

Fibonacci รุ่นเรียกซ้ำที่ไร้เดียงสาเป็นแบบยกกำลังโดยการออกแบบเนื่องจากการซ้ำซ้อนในการคำนวณ:

ที่รากคุณกำลังคำนวณ:

F (n) ขึ้นอยู่กับ F (n-1) และ F (n-2)

F (n-1) ขึ้นอยู่กับ F (n-2) อีกครั้งและ F (n-3)

F (n-2) ขึ้นอยู่กับ F (n-3) อีกครั้งและ F (n-4)

ถ้าคุณมีการเรียกซ้ำแบบเรียกซ้ำระดับ 2 แต่ละระดับซึ่งสูญเสียข้อมูลจำนวนมากในการคำนวณฟังก์ชันเวลาจะมีลักษณะดังนี้:

T (n) = T (n-1) + T (n-2) + C พร้อมค่าคงที่ C

T (n-1) = T (n-2) + T (n-3)> T (n-2) จากนั้น

T (n)> 2 * T (n-2)

...

T (n)> 2 ^ (n / 2) * T (1) = O (2 ^ (n / 2))

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

นอกจากนี้คุณสามารถค้นหาฟีโบนัชชีรุ่นที่ปรับให้เหมาะสมโดยใช้การเขียนโปรแกรมแบบไดนามิกเช่นนี้:

static int fib(int n)
{
    /* memory */
    int f[] = new int[n+1];
    int i;

    /* Init */
    f[0] = 0;
    f[1] = 1;

    /* Fill */
    for (i = 2; i <= n; i++)
    {
        f[i] = f[i-1] + f[i-2];
    }

    return f[n];
}

นั่นคือการปรับให้เหมาะสมและทำเพียงnขั้นตอน แต่ก็ยังเป็นที่ชี้แจง

ฟังก์ชันต้นทุนถูกกำหนดจากขนาดอินพุตจนถึงจำนวนขั้นตอนเพื่อแก้ไขปัญหา เมื่อคุณเห็นรุ่น Fibonacci แบบไดนามิก ( ขั้นตอนnในการคำนวณตาราง) หรืออัลกอริทึมที่ง่ายที่สุดที่จะรู้ว่าตัวเลขนั้นเป็นจำนวนเฉพาะ ( sqrt (n)เพื่อวิเคราะห์ตัวหารที่ถูกต้องของตัวเลขหรือไม่ คุณอาจคิดว่าอัลกอริทึมเหล่านี้คือO (n)หรือO (sqrt (n))แต่นี่ไม่ใช่ความจริงด้วยเหตุผลดังต่อไปนี้: อินพุตของอัลกอริทึมของคุณคือตัวเลข: nโดยใช้สัญกรณ์ไบนารีขนาดอินพุตสำหรับ จำนวนเต็มnคือlog2 (n)จากนั้นทำการเปลี่ยนแปลงตัวแปร

m = log2(n) // your real input size

ให้หาจำนวนขั้นตอนเป็นฟังก์ชั่นของขนาดอินพุต

m = log2(n)
2^m = 2^log2(n) = n

ดังนั้นค่าใช้จ่ายของอัลกอริทึมของคุณในฐานะฟังก์ชันของขนาดอินพุตคือ:

T(m) = n steps = 2^m steps

และนี่คือเหตุผลที่ต้นทุนเป็นเลขชี้กำลัง


1

มันง่ายในการคำนวณโดยการเรียกฟังก์ชั่นไดอะแกรม เพียงเพิ่มการเรียกใช้ฟังก์ชันสำหรับแต่ละค่าของ n และดูว่าจำนวนเพิ่มขึ้นอย่างไร

Big O คือ O (Z ^ n) โดยที่ Z คืออัตราส่วนทองคำหรือประมาณ 1.62

ทั้งตัวเลขเลโอนาร์โดและหมายเลขฟีโบนักชีเข้าใกล้อัตราส่วนนี้เมื่อเราเพิ่ม n

แตกต่างจากคำถาม Big O อื่น ๆ ไม่มีความแปรปรวนในอินพุตและทั้งอัลกอริทึมและการใช้อัลกอริทึมถูกกำหนดไว้อย่างชัดเจน

ไม่จำเป็นต้องมีคณิตศาสตร์ที่ซับซ้อนจำนวนมาก เพียงแสดงแผนภาพการเรียกใช้ฟังก์ชันด้านล่างและปรับฟังก์ชั่นให้ตรงกับหมายเลข

หรือถ้าคุณคุ้นเคยกับอัตราส่วนทองคำคุณจะจำได้เช่นนี้

คำตอบนี้ถูกต้องมากกว่าคำตอบที่ยอมรับซึ่งอ้างว่ามันจะเข้าหา f (n) = 2 ^ n มันจะไม่ มันจะเข้าใกล้ f (n) = golden_ratio ^ n

2 (2 -> 1, 0)

4 (3 -> 2, 1) (2 -> 1, 0)

8 (4 -> 3, 2) (3 -> 2, 1) (2 -> 1, 0)
            (2 -> 1, 0)


14 (5 -> 4, 3) (4 -> 3, 2) (3 -> 2, 1) (2 -> 1, 0)
            (2 -> 1, 0)

            (3 -> 2, 1) (2 -> 1, 0)

22 (6 -> 5, 4)
            (5 -> 4, 3) (4 -> 3, 2) (3 -> 2, 1) (2 -> 1, 0)
                        (2 -> 1, 0)

                        (3 -> 2, 1) (2 -> 1, 0)

            (4 -> 3, 2) (3 -> 2, 1) (2 -> 1, 0)
                        (2 -> 1, 0)

1
คุณสามารถให้แหล่งที่มาสำหรับการอ้างสิทธิ์นั้นเกี่ยวกับอัตราส่วนทองคำได้หรือไม่?
Nico Haase

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