Offer必备算法37_记忆化搜索_五道力扣题详解(由易到难)

目录

记忆化搜索概念和使用场景

①力扣509. 斐波那契数

解析代码1_循环

解析代码2_暴搜递归

解析代码3_记忆化搜索

解析代码4_动态规划

②力扣62. 不同路径

解析代码1_暴搜递归(超时)

解析代码2_记忆化搜索

解析代码3_动态规划

③力扣300. 最长递增子序列

解析代码1_爆搜递归(超时)

解析代码2_记忆化搜索

解析代码3_动态规划

④力扣375. 猜数字大小 II

解析代码1_爆搜递归(超时)

解析代码2_记忆化搜索

⑤力扣329. 矩阵中的最长递增路径

解析代码1_爆搜递归(超时)

解析代码2_记忆化搜索

本篇完。


记忆化搜索概念和使用场景

记忆化搜索是一种典型的空间换时间的思想,可以看成带备忘录的爆搜递归。

        搜索的低效在于没有能够很好地处理重叠子问题。在搜索过程中,会有很多重复计算,如果我们能记录一些状态的答案,就可以减少重复搜索量。动态规划虽然比较好地处理了重叠子问题,但是在有些拓扑关系比较复杂的题目面前,又显得无奈。记忆化搜索正是在这样的情况下产生的,它采用搜索的形式和动态规划中递推的思想将这两种方法有机地综合在一起,扬长避短,简单实用,在信息学中有着重要的作用。

        根据记忆化搜索的思想,它是解决重复计算,而不是重复生成,也就是说,这些搜索必须是在搜索扩展路径的过程中分步计算的题目,也就是“搜索答案与路径相关″的题目,而不能是搜索一个路径之后才能进行计算的题目,必须要分步计算,并且搜索过程中,一个搜索结果必须可以建立在同类型问题的结果上,也就是类似于动态规划解决的那种。

        记忆化搜索的典型应用场景是可能经过不同路径转移到相同状态的dfs问题。更明确地说,当我们需要在有层次结构的图(不是树,即当前层的不同节点可能转移到下一层的相同节点)中自上而下地进行dfs搜索时,大概率我们都可以通过记忆化搜索的技巧降低时间复杂度。

动态规划和记忆化搜索都是在爆搜的基础上优化。《算法导论》里也把记忆化搜索看成动态规划。


①力扣509. 斐波那契数

509. 斐波那契数

难度 简单

斐波那契数 (通常用 F(n) 表示)形成的序列称为 斐波那契数列 。该数列由 0 和 1 开始,后面的每一项数字都是前面两项数字的和。也就是:

F(0) = 0,F(1) = 1
F(n) = F(n - 1) + F(n - 2),其中 n > 1

给定 n ,请计算 F(n) 。

示例 1:

输入:n = 2
输出:1
解释:F(2) = F(1) + F(0) = 1 + 0 = 1

示例 2:

输入:n = 3
输出:2
解释:F(3) = F(2) + F(1) = 1 + 1 = 2

示例 3:

输入:n = 4
输出:3
解释:F(4) = F(3) + F(2) = 2 + 1 = 3

提示:

  • 0 <= n <= 30
class Solution {
public:
    int fib(int n) {

    }
};

解析代码1_循环

求斐波那契数是很经典的一道题,有多种解法。

        下面会从递归解法得出记忆化搜索解法,在得出动态规划解法,循环的解法也可以看作动态规划的状态压缩,完成闭环。

class Solution {
public:
    int fib(int n) {
        if (n < 2)
            return n;
        int fib1 = 0, fib2 = 0, ret = 1;
        for (int i = 2; i <= n; ++i)
        {
            fib1 = fib2;
            fib2 = ret;
            ret = fib1 + fib2;
        }
        return ret;
    }
};


解析代码2_暴搜递归

暴搜递归:

  • 递归含义:给 dfs 一个使命,给它一个数 n ,返回第 n 个斐波那契数的值。
  • 函数体:斐波那契数的递推公式。
  • 递归出口:当 n == 0 或者 n == 1 时,不用套公式。
class Solution {
public:
    int fib(int n) {
        return dfs(n);
    }

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


解析代码3_记忆化搜索

记忆化搜索:

  • 在递归的基础上加上一个备忘录(所以记忆化搜索也叫带备忘录的递归)。
  • 每次进入递归的时候,去备忘录里面看看。
  • 每次返回的时候,将结果加入到备忘录里面。
class Solution {
    int memo[31];
public:
    int fib(int n) {
        memset(memo, -1, sizeof(memo));
        return dfs(n);
    }

    int dfs(int n)
    {
        if(n <= 1)
            return n;
        if(memo[n] != -1)
            return memo[n];

        memo[n] = dfs(n - 1) + dfs(n - 2);
        return memo[n];
    }
};


解析代码4_动态规划

动态规划已经写过很多题了,这里根据记忆化搜索得出动态规划的解法:

  • 递归含义:状态表示
  • 函数体:状态转移方程
  • 递归出口:初始化
  • 填表顺序:填备忘录的顺序
  • 返回值:备忘录的值

        可以看出都是类似的,因为两者本质都是一样的,都是在爆搜的基础上优化。《算法导论》里也把记忆化搜索看成动态规划。

        所以很多时候都可以把爆搜递归的代码改成记忆化搜索,再改成动态规划,不过爆搜改记忆化搜索已经完成时间的优化了,没太多必要改成动态规划了。

class Solution {
public:
    int fib(int n) {
        if(n == 0)
            return 0;
        vector<int> dp(n + 1);
        dp[1] = 1;
        for(int i = 2; i <= n; ++i)
        {
            dp[i] = dp[i - 1] + dp[i - 2];
        }
        return dp[n];
    }
};


②力扣62. 不同路径

62. 不同路径

难度 中等

一个机器人位于一个 m x n 网格的左上角 (起始点在下图中标记为 “Start” )。

机器人每次只能向下或者向右移动一步。机器人试图达到网格的右下角(在下图中标记为 “Finish” )。

问总共有多少条不同的路径?

示例 1:

输入:m = 3, n = 7
输出:28

示例 2:

输入:m = 3, n = 2
输出:3
解释:
从左上角开始,总共有 3 条路径可以到达右下角。
1. 向右 -> 向下 -> 向下
2. 向下 -> 向下 -> 向右
3. 向下 -> 向右 -> 向下

示例 3:

输入:m = 7, n = 3
输出:28

示例 4:

输入:m = 3, n = 3
输出:6

提示:

  • 1 <= m, n <= 100
  • 题目数据保证答案小于等于 2 * 10^9
class Solution {
public:
    int uniquePaths(int m, int n) {

    }
};

解析代码1_暴搜递归(超时)

  • 递归含义:给 dfs 一个下标,返回从 [0, 0] 位置走到 [i, j] 位置一共有多少种方法。
  • 函数体:只要知道到达上面位置的方法数以及到达左边位置的方法数,然后累加起来即可。
  • 递归出口:当下标越界的时候返回 0 ,当位于起点的时候,返回 1 。
class Solution {
public:
    int uniquePaths(int m, int n) {
        return dfs(m, n);
    }

    int dfs(int sr, int sc)
    {
        if(sr == 0 || sc == 0)
            return 0;
        if(sr == 1 && sc == 1)
            return 1;
        return dfs(sr - 1, sc) + dfs(sr, sc - 1);
    }
};


解析代码2_记忆化搜索

记忆化搜索解法:

  • 加上一个备忘录。
  • 每次进入递归的时候,去备忘录里面看看。
  • 每次返回的时候,将结果加入到备忘录里面。
class Solution {
public:
    int uniquePaths(int m, int n) {
        vector<vector<int>> memo(m + 1, vector<int>(n + 1));
        return dfs(m, n, memo);
    }

    int dfs(int sr, int sc, vector<vector<int>>& memo)
    {
        if(sr == 0 || sc == 0)
            return 0;
        if(sr == 1 && sc == 1)
            return 1;

        if(memo[sr][sc] != 0)
            return memo[sr][sc];
        
        memo[sr][sc] = dfs(sr - 1, sc, memo) + dfs(sr, sc - 1, memo);
        return memo[sr][sc];
    }
};


解析代码3_动态规划

根据记忆化搜索得出动态规划的解法:

  • 递归含义:状态表示
  • 函数体:状态转移方程
  • 递归出口:初始化
  • 填表顺序:填备忘录的顺序
  • 返回值:备忘录的值
class Solution {
public:
    int uniquePaths(int m, int n) {
        vector<vector<int>> dp(m + 1, vector<int>(n + 1, 0));
        dp[1][1] = 1;
        for(int i = 1; i <= m; ++i)
        {
            for(int j = 1; j <= n; ++j)
            {
                if(i == 1 && j == 1)
                    continue;
                dp[i][j] = dp[i - 1][j] + dp[i][j - 1];
            }
        }
        return dp[m][n];
    }
};


③力扣300. 最长递增子序列

300. 最长递增子序列

难度 中等

给你一个整数数组 nums ,找到其中最长严格递增子序列的长度。

子序列 是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如,[3,6,2,7] 是数组 [0,3,1,6,2,2,7] 的子序列。 

示例 1:

输入:nums = [10,9,2,5,3,7,101,18]
输出:4
解释:最长递增子序列是 [2,3,7,101],因此长度为 4 。

示例 2:

输入:nums = [0,1,0,3,2,3]
输出:4

示例 3:

输入:nums = [7,7,7,7,7,7,7]
输出:1

提示:

  • 1 <= nums.length <= 2500
  • -10^4 <= nums[i] <= 10^4

进阶:

  • 你能将算法的时间复杂度降低到 O(n log(n)) 吗?
class Solution {
public:
    int lengthOfLIS(vector<int>& nums) {

    }
};

解析代码1_爆搜递归(超时)

  • 递归含义:给 dfs 一个数 i ,返回以 i 位置为起点的最长增子序列的长度。
  • 函数体:遍历 i 后面的所有位置,看谁能加到 i 这个元素的后面。统计所有情况下的最大值。
  • 递归出口:因为是判断之后再进入递归的,因此没有出口。
class Solution {
public:
    int lengthOfLIS(vector<int>& nums) {
        int sz = nums.size(), ret = 1;
        for(int i = 0; i < sz; ++i)
        {
            ret = max(ret, dfs(i, nums));
        }
        return ret;
    }

    int dfs(int pos, vector<int>& nums)
    {
        int sz = nums.size(), ret = 1;
        for(int i = pos + 1; i < sz; ++i)
        {
            if(nums[i] > nums[pos])
                ret = max(ret, dfs(i, nums) + 1);
        }
        return ret;
    }
};


解析代码2_记忆化搜索

记忆化搜索解法:

  • 加上一个备忘录。
  • 每次进入递归的时候,去备忘录里面看看。
  • 每次返回的时候,将结果加入到备忘录里面。
class Solution {
public:
    int lengthOfLIS(vector<int>& nums) {
        int sz = nums.size(), ret = 1;
        vector<int> memo(sz);
        for(int i = 0; i < sz; ++i)
        {
            ret = max(ret, dfs(i, nums, memo));
        }
        return ret;
    }

    int dfs(int pos, vector<int>& nums, vector<int>& memo)
    {
        if(memo[pos] != 0)
            return memo[pos];
        int sz = nums.size(), ret = 1;
        for(int i = pos + 1; i < sz; ++i)
        {
            if(nums[i] > nums[pos])
                ret = max(ret, dfs(i, nums, memo) + 1);
        }
        memo[pos] = ret;
        return ret;
    }
};


解析代码3_动态规划

根据记忆化搜索得出动态规划的解法:

  • 递归含义:状态表示
  • 函数体:状态转移方程
  • 递归出口:初始化
  • 填表顺序:填备忘录的顺序
  • 返回值:备忘录的值

        注意这里填表顺序有点不一样,因为记忆化搜索填pos位置的值的时候,依赖的是pos后面的值,所以动态规划解法的代码,填表顺序是从后往前填表。

class Solution {
public:
    int lengthOfLIS(vector<int>& nums) {
        int sz = nums.size(), ret = 1;
        vector<int> dp(sz, 1);
        for(int i = sz - 2; i >= 0; --i)
        {
            for(int j = i + 1; j < sz; ++j)
            {
                if(nums[j] > nums[i])
                    dp[i] = max(dp[i], dp[j] + 1);
            }
            ret = max(ret, dp[i]);
        }
        return ret;
    }
};


④力扣375. 猜数字大小 II

375. 猜数字大小 II

难度 中等

我们正在玩一个猜数游戏,游戏规则如下:

  1. 我从 1 到 n 之间选择一个数字。
  2. 你来猜我选了哪个数字。
  3. 如果你猜到正确的数字,就会 赢得游戏 。
  4. 如果你猜错了,那么我会告诉你,我选的数字比你的 更大或者更小 ,并且你需要继续猜数。
  5. 每当你猜了数字 x 并且猜错了的时候,你需要支付金额为 x 的现金。如果你花光了钱,就会 输掉游戏 。

给你一个特定的数字 n ,返回能够 确保你获胜 的最小现金数,不管我选择那个数字 。

示例 1:

输入:n = 10
输出:16
解释:制胜策略如下:
- 数字范围是 [1,10] 。你先猜测数字为 7 。
    - 如果这是我选中的数字,你的总费用为 $0 。否则,你需要支付 $7 。
    - 如果我的数字更大,则下一步需要猜测的数字范围是 [8,10] 。你可以猜测数字为 9 。
        - 如果这是我选中的数字,你的总费用为 $7 。否则,你需要支付 $9 。
        - 如果我的数字更大,那么这个数字一定是 10 。你猜测数字为 10 并赢得游戏,总费用为 $7 + $9 = $16 。
        - 如果我的数字更小,那么这个数字一定是 8 。你猜测数字为 8 并赢得游戏,总费用为 $7 + $9 = $16 。
    - 如果我的数字更小,则下一步需要猜测的数字范围是 [1,6] 。你可以猜测数字为 3 。
        - 如果这是我选中的数字,你的总费用为 $7 。否则,你需要支付 $3 。
        - 如果我的数字更大,则下一步需要猜测的数字范围是 [4,6] 。你可以猜测数字为 5 。
            - 如果这是我选中的数字,你的总费用为 $7 + $3 = $10 。否则,你需要支付 $5 。
            - 如果我的数字更大,那么这个数字一定是 6 。你猜测数字为 6 并赢得游戏,总费用为 $7 + $3 + $5 = $15 。
            - 如果我的数字更小,那么这个数字一定是 4 。你猜测数字为 4 并赢得游戏,总费用为 $7 + $3 + $5 = $15 。
        - 如果我的数字更小,则下一步需要猜测的数字范围是 [1,2] 。你可以猜测数字为 1 。
            - 如果这是我选中的数字,你的总费用为 $7 + $3 = $10 。否则,你需要支付 $1 。
            - 如果我的数字更大,那么这个数字一定是 2 。你猜测数字为 2 并赢得游戏,总费用为 $7 + $3 + $1 = $11 。
在最糟糕的情况下,你需要支付 $16 。因此,你只需要 $16 就可以确保自己赢得游戏。

示例 2:

输入:n = 1
输出:0
解释:只有一个可能的数字,所以你可以直接猜 1 并赢得游戏,无需支付任何费用。

示例 3:

输入:n = 2
输出:1
解释:有两个可能的数字 1 和 2 。
- 你可以先猜 1 。
    - 如果这是我选中的数字,你的总费用为 $0 。否则,你需要支付 $1 。
    - 如果我的数字更大,那么这个数字一定是 2 。你猜测数字为 2 并赢得游戏,总费用为 $1 。
最糟糕的情况下,你需要支付 $1 。

提示:

  • 1 <= n <= 200
class Solution {
public:
    int getMoneyAmount(int n) {

    }
};

解析代码1_爆搜递归(超时)

  • 递归含义:给 dfs 一个区间 [left, right] ,返回在这个区间上能完胜的最小费用
  • 函数体:选择 [left, right] 区间上的任意一个数作为头结点,然后递归分析左右子树。 求出所有情况下的最小值。因为要得到这个区间上能完胜的最小费用,所以选择左右子树时要求最大值。
  • 递归出口:当 left >= right 的时候,直接返回 0 。
class Solution {
public:
    int getMoneyAmount(int n) {
        return dfs(1, n);
    }

    int dfs(int left, int right)
    {
        if(left >= right)
            return 0;
        int ret = INT_MAX;
        for(int i = left; i <= right; ++i)
        {
            ret = min(ret, max(dfs(left, i - 1), dfs(i + 1, right)) + i);
        }
        return ret;
    }
};


解析代码2_记忆化搜索

记忆化搜索解法:

  • 加上一个备忘录。
  • 每次进入递归的时候,去备忘录里面看看。
  • 每次返回的时候,将结果加入到备忘录里面。
class Solution {
    int memo[201][201];
public:
    int getMoneyAmount(int n) {
        return dfs(1, n);
    }

    int dfs(int left, int right)
    {
        if(left >= right)
            return 0;
        if(memo[left][right] != 0)
            return memo[left][right];
        int ret = INT_MAX;
        for(int i = left; i <= right; ++i)
        {
            ret = min(ret, max(dfs(left, i - 1), dfs(i + 1, right)) + i);
        }
        memo[left][right] =ret;
        return ret;
    }
};


⑤力扣329. 矩阵中的最长递增路径

329. 矩阵中的最长递增路径

难度 困难

给定一个 m x n 整数矩阵 matrix ,找出其中 最长递增路径 的长度。

对于每个单元格,你可以往上,下,左,右四个方向移动。 你 不能 在 对角线 方向上移动或移动到 边界外(即不允许环绕)。

示例 1:

输入:matrix = [[9,9,4],[6,6,8],[2,1,1]]
输出:4 
解释:最长递增路径为 [1, 2, 6, 9]。

示例 2:

输入:matrix = [[3,4,5],[3,2,6],[2,2,1]]
输出:4 
解释:最长递增路径是 [3, 4, 5, 6]。注意不允许在对角线方向上移动。

示例 3:

输入:matrix = [[1]]
输出:1

提示:

  • m == matrix.length
  • n == matrix[i].length
  • 1 <= m, n <= 200
  • 0 <= matrix[i][j] <= 2^31 - 1
class Solution {
public:
    int longestIncreasingPath(vector<vector<int>>& matrix) {

    }
};

解析代码1_爆搜递归(超时)

  • 递归含义:给 dfs 一个下标 [i, j] ,返回从这个位置开始的最长递增路径的长度。
  • 函数体:上下左右四个方向看一看,哪里能过去就过去,统计四个方向上的最大长度。
  • 递归出口:因为是先判断再进入递归,因此没有出口。
class Solution {
    int dx[4] = {0, 0, -1, 1};
    int dy[4] = {1, -1, 0, 0};
    int m = 0, n = 0;
public:
    int longestIncreasingPath(vector<vector<int>>& matrix) {
        m = matrix.size(), n = matrix[0].size();
        int ret = 0;
        for(int i = 0; i < m; ++i)
        {
            for(int j = 0; j < n; ++j)
            {
                ret = max(ret, dfs(i, j, matrix));
            }
        }
        return ret + 1; // 加上自己
    }

    int dfs(int sr, int sc, vector<vector<int>>& matrix)
    {
        int ret = 0;
        for(int i = 0; i < 4; ++i)
        {
            int x = sr + dx[i], y = sc + dy[i];
            if(x >= 0 && x < m && y >= 0 && y < n && matrix[x][y] > matrix[sr][sc])
            {
                ret = max(ret, dfs(x, y, matrix) + 1);
            }
        }
        return ret;
    }
};


解析代码2_记忆化搜索

记忆化搜索解法:

  • 加上一个备忘录。
  • 每次进入递归的时候,去备忘录里面看看。
  • 每次返回的时候,将结果加入到备忘录里面。
class Solution {
    int dx[4] = {0, 0, -1, 1};
    int dy[4] = {1, -1, 0, 0};
    int m = 0, n = 0;
    int memo[201][201];
public:
    int longestIncreasingPath(vector<vector<int>>& matrix) {
        m = matrix.size(), n = matrix[0].size();
        int ret = 0;
        for(int i = 0; i < m; ++i)
        {
            for(int j = 0; j < n; ++j)
            {
                ret = max(ret, dfs(i, j, matrix));
            }
        }
        return ret + 1; // 加上自己
    }

    int dfs(int sr, int sc, vector<vector<int>>& matrix)
    {
        if(memo[sr][sc] != 0)
            return memo[sr][sc];
        int ret = 0;
        for(int i = 0; i < 4; ++i)
        {
            int x = sr + dx[i], y = sc + dy[i];
            if(x >= 0 && x < m && y >= 0 && y < n && matrix[x][y] > matrix[sr][sc])
            {
                ret = max(ret, dfs(x, y, matrix) + 1);
            }
        }
        memo[sr][sc] = ret;
        return ret;
    }
};


本篇完。

下一篇是贪心算法的第四部分。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/607792.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

最详尽的网络安全学习路线!涵盖所有技能点,带你成为网安专家!

目录 零基础小白&#xff0c;到就业&#xff01;入门到入土的网安学习路线&#xff01; 建议的学习顺序&#xff1a; 一、夯实一下基础&#xff0c;梳理和复习 二、HTML与JAVASCRIPT&#xff08;了解一下语法即可&#xff0c;要求不高&#xff09; 三、PHP入门 四、MYSQL…

QX-mini51单片机学习---(4)蜂鸣器

目录 1蜂鸣器工作原理 2三极管工作原理 3本节相关原理图分析 4实践 1蜂鸣器工作原理 2三极管工作原理 我们这里使用PNP三极管&#xff0c;低电压导通 做开关 PNP E&#xff08;emitrer&#xff09;&#xff1a;发射极&#xff0c;B&#xff08;base&#xff09;&#x…

leetcode每日一题第七十二天

class Solution { public:TreeNode* searchBST(TreeNode* root, int val) {if(!root) return root;if(root->val val) return root;else if(root->val > val) return searchBST(root->left,val);else return searchBST(root->right,val);} };

WPF中页面加载时由于TreeView页面卡顿

示例&#xff1a;右侧界面的数据根据左侧TreeView的选项加载不同的数据&#xff0c;页面加载时会把所有的数据加载一遍&#xff0c;导致页面卡顿。 解决办法&#xff1a; <Setter Property"IsSelected" Value"{Binding IsSelected}"/>

初学python记录:力扣1652. 拆炸弹

题目&#xff1a; 你有一个炸弹需要拆除&#xff0c;时间紧迫&#xff01;你的情报员会给你一个长度为 n 的 循环 数组 code 以及一个密钥 k 。 为了获得正确的密码&#xff0c;你需要替换掉每一个数字。所有数字会 同时 被替换。 如果 k > 0 &#xff0c;将第 i 个数字用…

车载测试到底怎么样?真实揭秘!

什么是车载智能系统测试&#xff1f; 车载智能系统&#xff0c;是汽车智能化重要的组成部分&#xff0c;由旧有的车载资通讯系统结合联网汽车技术所演进而来&#xff0c;随着软硬件技术的不断进步&#xff0c; 让车载智能系统拥有强大的运算能力及多元化的应用功能。 车载智能…

FreeRTOS学习 -- 任务相关API函数

一、任务创建和删除API函数 FreeRTOS 最基本的功能就是任务管理&#xff0c;而任务管理最基本的操作就是创建和删除任务。 FreeRTOS的任务创建和删除API函数如下&#xff1a; 1、函数 xTaskCreate() 此函数用来创建一个任务&#xff0c;任务需要 RAM 来保存于任务有关的状…

【C语言项目】贪吃蛇(上)

个人主页 ~ gitee仓库~ 欢迎大家来到C语言系列的最后一个篇章–贪吃蛇游戏的实现&#xff0c;当我们实现了贪吃蛇之后&#xff0c;我们的C语言就算是登堂入室了&#xff0c;基本会使用了&#xff0c;当然&#xff0c;想要更加熟练地使用还需要多多练习 贪吃蛇 一、目标二、需要…

Windows远程桌面实现之十四:实现AirPlay接收端,让苹果设备(iOS,iPad等)屏幕镜像到PC端

by fanxiushu 2024-05-04 转载或引用请注明原始作者。 这个课题已经持续了好几年&#xff0c;已经可以说是很长时间了。 实现的程序是 xdisp_virt&#xff0c; 可以去github下载使用:GitHub - fanxiushu/xdisp_virt: xfsredir file system 一开始是基于测试镜像驱动的目的随便开…

【Android】Kotlin学习之数据容器(数组创建)

kotlin数组 数组是一种初始化时指定容器大小, 不可以动态调整其大小的容器 数组创建

C++数据类型与表达式

一 C中的数据类型 二 基本数据类型 三 类型转换 各种类型的高低顺序如下所述; 四 构造数据类型 类类型

MYSQL-8.调优

性能优化思维 整体思维 木桶效应&#xff1a;系统的性能符合木桶效应&#xff08;一个木桶能装多少水&#xff0c;取决于木桶中最短的那块木板&#xff09;&#xff0c;所以性能优化需要从多个方面去考虑&#xff0c;如架构优化、业务优化、前端优化、中间件调优、网关优化、…

21物联1班常用网络命令

常用网络命令 ipconfig&#xff08;配置&#xff09;ping(测试)命令1&#xff1a;ping 172.16.0.12&#xff1a;ping ip -t3&#xff1a;ping ip -l 3000&#xff08;注意每个之间都存在空格&#xff09;4&#xff1a;ping ip -n count netstat&#xff08;网络&#xff09;命令…

初识C语言——第十六天

C语言中的语句结构类型:顺序/选择/循环 分支语句 if else switch 循环语句 while for do whlie goto语句 代码练习:找两个整数的最大公约数和最小公倍数 #define _CRT_SECURE_NO_WARNINGS #include <stdio.h>//int main() //{ // int age 60; // if (ag…

探索智能编程新境界:我与Baidu Comate的独特体验之旅

文章目录 一、认识Baidu Comate二、VS Code安装Baidu Comate教程三、Baidu Comate功能体验功能概览具体功能1.根据注释自动生成代码2.函数注释3.行间注释4.代码解释5.生成单元测试6.代码优化7.答疑解惑 四、交互体验五、总结 一、认识Baidu Comate ✨Baidu Comate插件是一款基…

激光跟踪仪在石油化工领域高效应用

管板式换热器是一种实现物料之间热量传递的节能设备&#xff0c;在石油化工行业生产过程中扮演着重要的角色。无论是在提高生产效率&#xff0c;保证产品质量还是节约能源方面&#xff0c;都发挥着重要作用。 测量需求 管板式热交换器内部有多个管板和折流板&#xff0c;每一…

一个递推通项公式研究

递推关系为a(n) ​pa(n−1) ​ qa(n−2) ​&#xff0c;本项前一项*2前前项&#xff0c;具体如 1&#xff0c;1&#xff0c;3&#xff0c;7&#xff0c;17&#xff0c;41&#xff0c;99&#xff0c;239&#xff0c;…… 一般的递推关系可以用以下方法 得两个解&#xff1a; …

火山引擎A/B测试平台的实验管理重构与DDD实践

本次分享的主题是火山引擎数智平台VeDI旗下的A/B测试平台 DataTester 实验管理架构升级与DDD实践。这里说明的一点是&#xff0c;代码的第一目标肯定是满足产品需求&#xff0c;能够满足产品需求的代码都是好代码。而本文中对代码的好坏的评价完全是从架构的视角&#xff0c;结…

AlphaFold3: Google DeepMind的的新突破

AlphaFold 3的论文今天在Nature期刊发表啦!这可是AI在生物领域最厉害的突破的最新版本。AlphaFold-3的新招就是用扩散模型去"画出"分子的结构。它一开始先从一团模模糊糊的原子云下手,然后慢慢透过去噪把分子变得越来越清楚。 Alphafold3 我们活在一个从Llama和Sora那…

Baidu Comate智能编码助手:大学生的代码编写助手

Baidu Comate智能编码助手&#xff1a;大学生的代码编写助手 前言一、关于Baidu Comate智能编码助手1.1 Baidu Comate智能编码助手简介1.2 产品功能 二、安装使用&#xff08;本文以pycharm为例&#xff09;三、我的百度Comate之旅3.1智能推荐3.1.1 单行推荐3.1.2 多行推荐 3.2…