Fancy DSA Fancy DSA
数据结构
算法
LeetCode
  • 关于
  • 导航 (opens new window)
  • 分类
  • 标签
  • 归档
设计模式 (opens new window)
博客 (opens new window)
GitHub (opens new window)

Jonsam NG

想的更多,也要想的更远
数据结构
算法
LeetCode
  • 关于
  • 导航 (opens new window)
  • 分类
  • 标签
  • 归档
设计模式 (opens new window)
博客 (opens new window)
GitHub (opens new window)
  • 开始上手
  • Plan 计划
  • Roadmap 路线
  • 算法简介
  • Sort 排序

  • Search 搜索

  • Recursive 递归

  • Graph 图

  • Tree 树

  • Math 数学

  • Hash 哈希

  • String 字符串

  • BitManipulation 位操纵

  • Backtracking 回溯

  • DynamicProgramming 动态规划

    • ClimbingStairs [爬楼梯]
    • CoinChange [钱币兑换]
    • EditDistance [编辑距离]
    • FibonacciNumber [斐波那契数]
    • FindMonthCalendar [月历]
    • KadaneAlgo [最大连续子数组和之Kadane算法]
    • LevenshteinDistance [莱文斯坦距离]
    • LongestCommonSubsequence [最长公共子序列]
    • LongestIncreasingSubsequence [最长递增子序列]
    • LongestPalindromicSubsequence [最长回文子序列]
    • LongestValidParentheses [最长合法括号]
    • MaxNonAdjacentSum [最大非连接子集和]
    • MaxProductOfThree [最大三数积]
    • MinimumCostPath [最小代价路径]
    • NumberOfSubsetEqualToGivenSum [等和子集]
    • RodCutting [棒材切割问题]
    • Shuf [随机样本]
    • SieveOfEratosthenes [埃拉托斯特尼筛法]
    • SlidingWindow [滑窗]
    • SudokuSolver [数独]
    • TrappingRainWater [接住雨水]
    • TribonacciNumber [翠波那契数]
      • 介绍
      • 实现
      • 参考
    • ZeroOneKnapsack [零一背包]
  • Cache 缓存

  • Array 数组

  • Ciphers 密码学

  • Conversions 转换

  • ProjectEuler 欧拉计划

  • 其他

  • 算法
  • DynamicProgramming 动态规划
jonsam
2022-09-26
目录

TribonacciNumber [翠波那契数]

# 介绍

泰波那契数列是斐波那契数列的一般化,其中每项都是前面三项的总和。其一般形式为 a(n) = a(n-1) + a(n-2) + a(n-3) 。

翠波那契序列:

0, 0, 1, 1, 2, 4, 7, 13, 24, 44, 81, 149, 274, 504, 927, 1705, 3136, 5768, 10609, 19513, 35890, 66012, 121415, 223317, 410744, 755476, 1389537, 2555757, 4700770, 8646064, 15902591, 29249425, 53798080, 98950096, 181997601, 334745777, 615693474, 1132436852... 以此类推。

# 实现

一个简单的解决方案是递归。

// A simple recursive Javascript program to print first n Tribinocci numbers.
 
function printTribRec(n) {
    if (n == 0 || n == 1 || n == 2) return 0;
    if (n == 3) return 1;
    return printTribRec(n - 1) + printTribRec(n - 2) + printTribRec(n - 3);
}
1
2
3
4
5
6
7

使用动态规划:

Top-Down Dp Memoization:

function printTribRec(n, dp) {
    if (n == 0 || n == 1 || n == 2) return 0;
    if(dp[n] != -1) return dp[n];
    if (n == 3) return 1;
    return dp[n] = printTribRec(n - 1, dp) + printTribRec(n - 2, dp) + printTribRec(n - 3, dp);
}
1
2
3
4
5
6

Bottom-Up DP Tabulation:

function printTrib(n) {
  let dp = Array.from({length: n}, (_, i) => 0);
  dp[0] = dp[1] = 0;
  dp[2] = 1;

  for (let i = 3; i < n; i++) dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3];
  return dp;
}
1
2
3
4
5
6
7
8

或者:

/**
 * @function Tribonacci
 * @description Tribonacci is the sum of previous three tribonacci numbers.
 * @param {Integer} n - The input integer
 * @return {Integer} tribonacci of n.
 * @see [Tribonacci_Numbers](https://www.geeksforgeeks.org/tribonacci-numbers/)
 */
const tribonacci = (n) => {
  // creating array to store previous tribonacci numbers
  const dp = new Array(n + 1)
  dp[0] = 0
  dp[1] = 1
  dp[2] = 1
  for (let i = 3; i <= n; i++) dp[i] = dp[i - 1] + dp[i - 2] + dp[i - 3]
  return dp[n]
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

上述的时间复杂度是线性的,但它需要额外的空间。我们可以使用三个变量来跟踪前三个数字,以优化上述解决方案的空间。

// A space optimized based Javascript program to print first n Tribonacci numbers.
function printTrib(n) {
    if (n < 1) return;
    // Initialize first three numbers
    let first = 0, second = 0, third = 1;
    // Loop to add previous three numbers for each number starting from 3 and then assign first, second, third to second, third, and curr to third respectively
    for (let i = 3; i < n; i++) {
      let curr = first + second + third;
      first = second;
      second = third;
      third = curr;
    }

    return third;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

更有效的解决方案:使用矩阵指数化。

// javascript Program to print first n tribonacci numbers
// Matrix Multiplication function for 3*3 matrix
function multiply(T , M) {
    var a, b, c, d, e, f, g, h, i;
    a = T[0][0] * M[0][0] + T[0][1] * M[1][0] + T[0][2] * M[2][0];
    b = T[0][0] * M[0][1] + T[0][1] * M[1][1] + T[0][2] * M[2][1];
    c = T[0][0] * M[0][2] + T[0][1] * M[1][2] + T[0][2] * M[2][2];
    d = T[1][0] * M[0][0] + T[1][1] * M[1][0] + T[1][2] * M[2][0];
    e = T[1][0] * M[0][1] + T[1][1] * M[1][1] + T[1][2] * M[2][1];
    f = T[1][0] * M[0][2] + T[1][1] * M[1][2] + T[1][2] * M[2][2];
    g = T[2][0] * M[0][0] + T[2][1] * M[1][0] + T[2][2] * M[2][0];
    h = T[2][0] * M[0][1] + T[2][1] * M[1][1] + T[2][2] * M[2][1];
    i = T[2][0] * M[0][2] + T[2][1] * M[1][2] + T[2][2] * M[2][2];
    T[0][0] = a;
    T[0][1] = b;
    T[0][2] = c;
    T[1][0] = d;
    T[1][1] = e;
    T[1][2] = f;
    T[2][0] = g;
    T[2][1] = h;
    T[2][2] = i;
}
 
// Recursive function to raise the matrix T to the power n
function power(T , n) {
    // base condition.
    if (n == 0 || n == 1) return;
    var M = [[ 1, 1, 1 ], [ 1, 0, 0 ], [ 0, 1, 0 ]];
    // recursively call to square the matrix
    power(T, parseInt(n / 2));
    // calculating square of the matrix T
    multiply(T, T);
    // if n is odd multiply it one time with M
    if (n % 2 != 0) multiply(T, M);
}
function tribonacci(n) {
    var T = [[ 1, 1, 1 ], [ 1, 0, 0 ], [ 0, 1, 0 ]];
    // base condition
    if (n == 0 || n == 1) return 0;
    else power(T, n - 2);
    // T[0][0] contains the tribonacci number so return it
    return T[0][0];
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44

参考:Matrix Exponentiation - GeeksforGeeks (opens new window)。

# 参考

  • Tribonacci Numbers - GeeksforGeeks (opens new window)
  • Tribonacci Number -- from Wolfram MathWorld (opens new window)
  • Fibonacci Number -- from Wolfram MathWorld (opens new window)
编辑 (opens new window)
上次更新: 2022/10/27, 20:28:55
TrappingRainWater [接住雨水]
ZeroOneKnapsack [零一背包]

← TrappingRainWater [接住雨水] ZeroOneKnapsack [零一背包]→

最近更新
01
0-20题解
10-31
02
本章导读
10-31
03
算法与转换:Part1
10-28
更多文章>
Theme by Vdoing | Copyright © 2022-2022 Fancy DSA | Made by Jonsam by ❤
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式