【经典算法】LeetCode 64. 最小路径和(Java/C/Python3/Golang实现含注释说明,Easy)

news2024/12/28 19:24:56
  • 作者主页: 🔗进朱者赤的博客

  • 精选专栏:🔗经典算法

  • 作者简介:阿里非典型程序员一枚 ,记录在大厂的打怪升级之路。 一起学习Java、大数据、数据结构算法(公众号同名

  • ❤️觉得文章还不错的话欢迎大家点赞👍➕收藏⭐️➕评论,💬支持博主,记得点个大大的关注,持续更新🤞
    ————————————————-

文章目录

  • 题目描述
  • 思路及实现
    • 方式一:动态规划(朴素DP )
      • 思路
      • 代码实现
        • Java版本
        • C语言版本
        • Python3版本
        • go
      • 复杂度分析
    • 方式二:滚动数组优化DP
      • 思路
      • 代码实现
        • Java版本
        • C语言版本
        • Python3版本
        • go
      • 复杂度分析
  • 总结
  • 相似题目

  • 标签(题目类型):动态规划

题目描述

给定一个包含非负整数的 m x n 网格 grid ,请找出一条从左上角到右下角的路径,
使得路径上的数字总和为最小。

在这里插入图片描述

说明:每次只能向下或者向右移动一步。
 

示例 1:

输入:grid = [[1,3,1],[1,5,1],[4,2,1]]
输出:7
解释:因为路径 1→3→1→1→1 的总和最小。
示例 2:

输入:grid = [[1,2,3],[4,5,6]]
输出:12
 

提示:

m == grid.length
n == grid[i].length
1 <= m, n <= 200
0 <= grid[i][j] <= 200

原题:LeetCode 64.最小路径和

思路及实现

方式一:动态规划(朴素DP )

思路

可以使用动态规划来求解最小路径和。

要求从左上角转移到右下角的最小路径和,每次只能往右走或者往下走。换句话说,对于位置 (i, j),其只能从 (i-1, j) 和 (i, j-1) 两个位置转移而来。我们设 dp[i][j] 表示到达位置 (i, j) 的最小路径和。
那么 dp[i][j] 肯定要从 dp[i-1][j] 和 dp[i][j-1] 中那个更小的状态转移过来,
因此状态转移方程为:dp[i][j] = min(dp[i][j-1], dp[i-1][j]) + grid[i][j]
在这里插入图片描述
边界条件:

  • 当 i = 0, j = 0 时,即左上角位置,其左侧和上侧单元格都不存在,dp[0][0] = grid[0][0]
  • 当 i = 0, j ≠ 0 时,即首行元素,其上侧单元格不存在,dp[0][j] = dp[0][j-1] + grid[0][j];
  • 当 i ≠ 0, j = 0 时,即首列元素,其左侧单元格不存在,dp[i][0] = dp[i-1][0] + grid[i][0];

代码实现

Java版本
public class Solution {
    public int minPathSum(int[][] grid) {
        if (grid == null || grid.length == 0 || grid[0].length == 0) {
            return 0;
        }

        int m = grid.length;
        int n = grid[0].length;
        int[][] dp = new int[m][n];

        // 初始化第一行和第一列
        //初始化第一个元素
        dp[0][0] = grid[0][0];
         // 初始化第一行
        for (int i = 1; i < m; i++) {
            dp[i][0] = dp[i - 1][0] + grid[i][0];
        }
         // 初始化第一列
        for (int j = 1; j < n; j++) {
            dp[0][j] = dp[0][j - 1] + grid[0][j];
        }

        // 填充其他位置
        for (int i = 1; i < m; i++) {
            for (int j = 1; j < n; j++) {
                dp[i][j] = Math.min(dp[i - 1][j], dp[i][j - 1]) + grid[i][j];
            }
        }
        // 最后一个元素即结果
        return dp[m - 1][n - 1];
    }
}

说明:
此解法使用动态规划,时间复杂度为 O(mn),空间复杂度也为 O(mn)。

C语言版本
#include <stdio.h>
#include <limits.h>

int minPathSum(int** grid, int gridSize, int* gridColSize){
    if (grid == NULL || gridSize == 0 || gridColSize[0] == 0) {
        return 0;
    }

    int m = gridSize;
    int n = gridColSize[0];
    int** dp = (int**)malloc(m * sizeof(int*));
    for (int i = 0; i < m; i++) {
        dp[i] = (int*)malloc(n * sizeof(int));
    }

    // 初始化第一行和第一列
    dp[0][0] = grid[0][0];
    for (int i = 1; i < m; i++) {
        dp[i][0] = dp[i - 1][0] + grid[i][0];
    }
    for (int j = 1; j < n; j++) {
        dp[0][j] = dp[0][j - 1] + grid[0][j];
    }

    // 填充其他位置
    for (int i = 1; i < m; i++) {
        for (int j = 1; j < n; j++) {
            dp[i][j] = (dp[i - 1][j] < dp[i][j - 1]) ? (dp[i - 1][j] + grid[i][j]) : (dp[i][j - 1] + grid[i][j]);
        }
    }

    int result = dp[m - 1][n - 1];

    // 释放动态分配的内存
    for (int i = 00; i < m; i++) {
        free(dp[i]);
    }
    free(dp);

    return result;
}

int main() {
    // 示例网格
    int gridSize = 3;
    int gridColSize[3] = {3, 3, 3};
    int grid[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};
    int** gridPtr = (int**)malloc(gridSize * sizeof(int*));
    for (int i = 0; i < gridSize; i++) {
        gridPtr[i] = grid[i];
    }

    int minSum = minPathSum(gridPtr, gridSize, gridColSize);
    printf("The minimum path sum is: %d\n", minSum);

    // 释放动态分配的内存
    free(gridPtr);

    return 0;
}

说明:
C语言版本同样使用动态规划,时间复杂度和空间复杂度与Java版本相同。注意在C语言中需要手动管理内存,因此在函数结束时需要释放动态分配的内存。

Python3版本
def minPathSum(grid):
    if not grid or not grid[0]:
        return 0

    m, n = len(grid), len(grid[0])
    dp = [[0] * n for _ in range(m)]

    # 初始化第一行和第一列
    dp[0][0] = grid[0][0]
    for i in range(1, m):
        dp[i][0] = dp[i - 1][0] + grid[i][0]
    for j in range(1, n):
        dp[0][j] = dp[0][j - 1] + grid[0][j]

    # 填充其他位置
    for i in range(1, m):
        for j in range(1, n):
            dp[i][j] = min(dp[i - 1][j], dp[i][j - 1]) + grid[i][j]

    return dp[m - 1][n - 1]

# test
# 示例网格
grid = [
    [1, 3, 1],
    [1, 5, 1],
    [4, 2, 1]
]

min_sum = minPathSum(grid)
print(f"The minimum path sum is: {min_sum}")

说明:
Python3版本使用动态规划,简洁易懂。由于Python中的列表支持动态大小,因此不需要手动管理内存。

go
// minPathSum 使用朴素DP方法求解最小路径和
func minPathSum(grid [][]int) int {
    if len(grid) == 0 || len(grid[0]) == 0 {
        return 0
    }
    rows, cols := len(grid), len(grid[0])
    
    // 创建一个二维DP数组,大小与grid相同,用于存储到达每个位置的最小路径和
    dp := make([][]int, rows)
    for i := range dp {
        dp[i] = make([]int, cols)
    }
    
    // 初始化第一行和第一列
    dp[0][0] = grid[0][0]
    for i := 1; i < rows; i++ {
        dp[i][0] = dp[i-1][0] + grid[i][0] // 第一列的最小路径和依赖于上一行的值
    }
    for j := 1; j < cols; j++ {
        dp[0][j] = dp[0][j-1] + grid[0][j] // 第一行的最小路径和依赖于前一列的值
    }
    
    // 填充剩余的DP数组
    for i := 1; i < rows; i++ {
        for j := 1; j < cols; j++ {
            // 当前位置的最小路径和取上方和左方位置的最小路径和加上当前位置的值
            dp[i][j] = min(dp[i-1][j], dp[i][j-1]) + grid[i][j]
        }
    }
    
    // 返回右下角位置的最小路径和
    return dp[rows-1][cols-1]
}

// min 返回两个整数中的较小值
func min(a, b int) int {
    if a < b {
        return a
    }
    return b
}

// 示例使用
func main() {
    grid := [][]int{
        {1, 3, 1},
        {1, 5, 1},
        {4, 2, 1},
    }
    minSum := minPathSum(grid)
    fmt.Printf("The minimum path sum is: %d\n", minSum)
}

说明:
minPathSum:使用朴素DP算法计算从grid左上角到右下角的最小路径和。
逻辑步骤

  1. 初始化二维DP数组dp,大小与grid相同。
  2. 填充dp数组的第一行和第一列。
  3. 遍历grid剩余元素,根据状态转移方程填充dp数组。
  4. 返回dp数组的右下角元素作为结果。

复杂度分析

  • 时间复杂度:O(mn),其中 m 和 n 分别是网格的行数和列数。需要遍历每个网格位置一次。
  • 空间复杂度:O(mn),需要一个二维数组 dp 来存储每个位置的最小路径和。

方式二:滚动数组优化DP

对于上述的动态规划解法,我们注意到在计算 dp[i][j] 时,只依赖于其正上方和左方的值。因此,我们可以使用滚动数组来优化空间复杂度,将空间复杂度从 O(mn) 降低到 O(n)。

思路

由于每一行的计算只依赖于上一行的值,我们可以只保留上一行的值,并在当前行上直接计算。这样,我们只需要一个一维数组来存储上一行的值即可。

代码实现

Java版本
public int minPathSum(int[][] grid) {
    if (grid == null || grid.length == 0 || grid[0].length == 0) {
        return 0;
    }

    int m = grid.length;
    int n = grid[0].length;
    int[] dp = new int[n];

    // 初始化第一行
    dp[0] = grid[0][0];
    for (int j = 1; j < n; j++) {
        dp[j] = dp[j - 1] + grid[0][j];
    }

    // 填充其他行
    for (int i = 1; i < m; i++) {
        int prev = dp[0]; // 保存上一行的第一个值,因为下一个dp[0]会被覆盖
        for (int j = 0; j < n; j++) {
            int curr = dp[j]; // 保存当前位置的值,因为下一个dp[j]会被覆盖
            if (j == 0) {
                // 如果是第一列,则只能从上方来
                dp[j] = prev + grid[i][j];
            } else {
                // 否则取上方和左方的最小值
                dp[j] = Math.min(prev, dp[j]) + grid[i][j];
            }
            prev = curr; // 更新prev为下一个位置的上一行值
        }
    }

    // dp数组的最后一个元素即为最小路径和
    return dp[n - 1];
}
C语言版本
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>

int minPathSum(int** grid, int gridSize, int* gridColSize) {
    if (grid == NULL || gridSize == 0 || gridColSize[0] == 0) {
        return 0;
    }

    int n = gridColSize[0];
    int* dp = (int*)malloc(n * sizeof(int));
    if (dp == NULL) {
        return -1;
    }

    // 初始化第一行
    dp[0] = grid[0][0];
    for (int j = 1; j < n; j++) {
        dp[j] = dp[j - 1] + grid[0][j];
    }

    // 填充其他行
    for (int i = 1; i < gridSize; i++) {
        int prev = dp[0]; // 保存上一行的第一个值
        for (int j = 0; j < n; j++) {
            int temp = dp[j]; // 临时保存当前位置的值
            if (j == 0) {
                dp[j] = prev + grid[i][j];
            } else {
                dp[j] = (prev < dp[j]) ? (prev + grid[i][j]) : (dp[j] + grid[i][j]);
            }
            prev = temp; // 更新prev
        }
    }

    int result = dp[n - 1];
    free(dp);
    return result;
}

int main() {
    int gridSize = 3;
    int gridColSize[3] = {3, 3, 3};
    int grid[3][3] = {{1, 3, 1}, {1, 5, 1}, {4, 2, 1}};
    int** gridPtr = (int**)malloc(gridSize * sizeof(int*));
    for (int i = 0; i < gridSize; i++) {
        gridPtr[i] = (int*)malloc(gridColSize[i] * sizeof(int));
        for (int j = 0; j < gridColSize[i]; j++) {
            gridPtr[i][j] = grid[i][j];
        }
    }

    int minSum = minPathSum(gridPtr, gridSize, gridColSize);
    printf("The minimum path sum is: %d\n", minSum);

    // 释放动态分配的内存
    for (int i = 0; i < gridSize; i++) {
        free(gridPtr[i]);
    }
    free(gridPtr);

    return 0;
}
Python3版本
def minPathSum(grid):
    if not grid or not grid[0]:
        return 0

    m, n = len(grid), len(grid[0])
    dp = [0] * n

    # 初始化第一行
    dp[0] = grid[0][0]
    for j in range(1, n):
        dp[j] = dp[j - 1] + grid[0][j]

    # 填充其他行
    for i in range(1, m):
        prev = dp[0]
        for j in range(n):
            curr = dp[j]
            dp[j] = prev + grid[i][j] if j == 0 else min(prev, dp[j]) + grid[i][j]
            prev = curr

    return dp[n - 1]

# 示例网格
grid = [
    [1, 3, 1],[1, 5, 1],
    [4, 2, 1]
]

min_sum = minPathSum(grid)
print(f"The minimum path sum is: {min_sum}")
go
// minPathSumOpt 使用滚动数组优化DP方法求解最小路径和
func minPathSumOpt(grid [][]int) int {
    if len(grid) == 0 || len(grid[0]) == 0 {
        return 0
    }
    rows, cols := len(grid), len(grid[0])
    
    // 只需要一个一维数组来保存当前行的最小路径和
    prevRow := make([]int, cols)
    currRow := make([]int, cols)
    
    // 初始化第一列
    prevRow[0] = grid[0][0]
    for j := 1; j < cols; j++ {
        prevRow[j] = prevRow[j-1] + grid[0][j]
    }
    
    // 填充剩余的行
    for i := 1; i < rows; i++ {
        // 交换prevRow和currRow,currRow用于保存当前行的最小路径和
        prevRow, currRow = currRow, prevRow
        
        // 初始化当前行的第一列
        currRow[0] = prevRow[0] + grid[i][0]
        
        // 填充当前行的剩余列
        for j := 1; j < cols; j++ {
            // 当前位置的最小路径和取上方和左方位置的最小路径和加上当前位置的值
            currRow[j] = min(prevRow[j], currRow[j-1]) + grid[i][j]
        }
    }
    
    // 返回最后一行的最后一个元素,即最小路径和
    return currRow[cols-1]
}

// min 返回两个整数中的较小值
func min(a, b int) int {
    if a < b {
        return a
    }
    return b
}

// 示例使用
func main() {
    grid := [][]int{
        {1, 3, 1},
        {1, 5, 1},
        {4, 2, 1},
}
minSum := minPathSumOpt(grid)
fmt.Printf("The minimum path sum with rolling array optimization is: %d\n", minSum)
}

说明:
函数功能
minPathSumOpt:使用滚动数组优化DP算法计算从grid左上角到右下角的最小路径和。
步奏

  1. 初始化两个一维数组prevRowcurrRow
  2. 填充prevRow数组作为第一行的最小路径和。
  3. 遍历grid剩余行,交替使用prevRowcurrRow计算最小路径和。
  4. 返回currRow的最后一个元素作为结果。

复杂度分析

  • 时间复杂度:O(mn),其中 m 和 n 分别是网格的行数和列数。仍然需要遍历每个网格位置一次。
  • 空间复杂度:O(n),其中 n 是网格的列数。使用滚动数组只需要存储一行的值。

滚动数组优化后的空间复杂度更低,但时间复杂度保持不变。这种优化在处理大规模网格时尤其有用,因为它显著减少了内存的使用。

总结

解法思路特点优点缺点时间复杂度空间复杂度
朴素DP填充DP表,状态转移每个位置的状态取决于上方和左方直观易懂空间占用大O(mn)O(mn)
滚动数组优化DP只用一维数组,通过循环更新节省空间,利用上一行的值节省空间编程稍微复杂O(mn)O(n)

相似题目

相似题目难度链接
leetcode 349 两个数组的交集简单力扣-349
leetcode 62 不同路径中等力扣-62
leetcode 63 不同路径 II中等力扣-63
leetcode 64 最小路径和中等力扣-64
leetcode 120 三角形最小路径和中等力扣-120
leetcode 152 乘积最大子数组中等力扣-152
leetcode 198 打家劫舍中等力扣-198
leetcode 213 打家劫舍 II困难力扣-213
leetcode 300 最长递增子序列中等力扣-300
leetcode 309 最佳买卖股票时机含冷冻期中等力扣-309

这些题目都涉及到动态规划的思想,有些题目可能需要使用滚动数组进行优化,有些题目则需要根据特定条件调整状态转移方程。通过练习这些题目,可以加深对动态规划的理解和掌握。

在这里插入图片描述

欢迎一键三连(关注+点赞+收藏),技术的路上一起加油!!!代码改变世界

  • 关于我:阿里非典型程序员一枚 ,记录在大厂的打怪升级之路。 一起学习Java、大数据、数据结构算法(公众号同名),回复暗号,更能获取学习秘籍和书籍等

  • —⬇️欢迎关注下面的公众号:进朱者赤,认识不一样的技术人。⬇️—

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

java文件夹文件比较工具

import java.io.BufferedReader; import java.io.File; import java.io.FileReader; import java.io.IOException; import java.util.HashSet; import java.util.Set;public class FolderFileNames {public static void main(String[] args) {// 假设您要读取的文件夹路径是 &q…

代码随想录-算法训练营day12【休息,复习与总结】

代码随想录-035期-算法训练营【博客笔记汇总表】-CSDN博客 ● day 12 周日休息&#xff08;4.14&#xff09; 目录 复习与总结 0417_图论-太平洋大西洋水流问题 0827_图论-最大人工岛 复习与总结 二刷做题速度提升了一大截&#xff0c;ヾ(◍∇◍)&#xff89;&#xff9e;加…

【IDEA】JRebel LS client not configured

主要原因就是因为 jrebel 的版本跟 idea的版本对不上&#xff0c;或者说jrebel的版本比idea的版本还高&#xff0c;导致出现该错误 查看idea版本 ![在这里插入图片描述](https://img-blog.csdnimg.cn/direct/a7ba43e6822947318cdb0d0e9d8d65e9.png 获取jrebel 版本 如何处理 …

设计模式:简单工厂模式(Simple Factory)

设计模式&#xff1a;简单工厂模式&#xff08;Simple Factory&#xff09; 设计模式&#xff1a;简单工厂模式&#xff08;Simple Factory&#xff09;模式动机模式定义模式结构时序图模式实现测试模式分析实例&#xff1a;Qt 控件类优缺点适用环境模式应用 设计模式&#xff…

李沐-26 网络中的网络 NiN【动手学深度学习v2】

主要记载关于全局平均池化层&#xff08;Global Average Pooling, GAP&#xff09;中如下两点的理解&#xff1a; 1. GAP的原理 2. 相对于全连接层&#xff0c;GAP具有更少的参数 为了直观地说明全局平均池化层相对于全连接层具有更少的参数&#xff0c;我们可以构造一个简…

博客文章:AWS re:Invent 2023 新产品深度解析 - 第四部分

TOC &#x1f308;你好呀&#xff01;我是 是Yu欸 &#x1f30c; 2024每日百字篆刻时光&#xff0c;感谢你的陪伴与支持 ~ &#x1f680; 欢迎一起踏上探险之旅&#xff0c;挖掘无限可能&#xff0c;共同成长&#xff01; 写在最前面 去年发布文章的一部分&#xff0c;由于内…

bugku-web-login2

这里提示是命令执行 抓包发现有五个报文 其中login.php中有base64加密语句 $sql"SELECT username,password FROM admin WHERE username".$username.""; if (!empty($row) && $row[password]md5($password)){ } 这里得到SQL语句的组成&#xff0c;…

SOLIDWORKS批量改名工具个人版 慧德敏学

每个文件都会有自己的名字&#xff0c;SOLIDWOKRKS模型也不例外。但是如果从资源管理器直接修改模型的文件名&#xff0c;就会导致模型关联的丢失&#xff0c;导致装配体打开之后找不到模型&#xff0c;因此就需要使用SOLIDWORKS的重命名功能。 SOLIDWORKS批量改名插件- Solid…

Blazor 下的 Json 编辑器

最近恰好碰到个比较冷门的需求&#xff0c;就是在线编码 Json&#xff0c;这其中有Json的语法着色&#xff0c;有Json对象属性数据类型的限制&#xff0c;其实要是单纯改一下Json字符串也不是难事&#xff0c;就是没法控制让用户只能给属性值&#xff0c;而不是属性名称&#x…

【随笔】Git 高级篇 -- 远程服务器拒绝 git push reset(三十二)

&#x1f48c; 所属专栏&#xff1a;【Git】 &#x1f600; 作  者&#xff1a;我是夜阑的狗&#x1f436; &#x1f680; 个人简介&#xff1a;一个正在努力学技术的CV工程师&#xff0c;专注基础和实战分享 &#xff0c;欢迎咨询&#xff01; &#x1f496; 欢迎大…

C++:仿函数模拟实现STL-priority_queue

优先级队列模拟实现 1.文档了解2.仿函数实现优先级队列仿函数1.定义2.语法3.使用 3.模拟实现源码 1.文档了解 从priority_queue的文档中&#xff0c;我们可以得出以下几点&#xff1a; 1.priority_queue是一个容器适配器 2.priority_queue它实质是一个堆&#xff0c;且默认为大…

【Leetcode】string类刷题

&#x1f525;个人主页&#xff1a;Quitecoder &#x1f525;专栏&#xff1a;Leetcode刷题 目录 1.仅反转字母2.字符串中第一个唯一字符3.验证回文串4.字符串相加5.反转字符串I I6.反转字符串中的单词III7.字符串相乘8.把字符串转换为整数 1.仅反转字母 题目链接&#xff1a;…

MySQL 8.0.19安装教程(windows 64位)

在c盘目录下的Program Files目录下创建MySQL目录&#xff0c;将下载好的mysql解压到里面 解压完是这个样子 配置初始化的my.ini文件的文件 [mysqld] # 设置3306端口 port3306 # 设置mysql的安装目录 basedirC:\Program Files\MySQL # 设置mysql数据库的数据的存放目录 datad…

便携式手提万兆网络协议测试仪

便携式手提万兆网络协议测试仪 平台简介 便携式手提万兆网络协议测试仪&#xff0c;以FPGA万兆卡和X86主板为基础&#xff0c;构建便携式的手提设备。 FPGA万兆卡是以Kintex-7XC7K325T PCIeX4的双路万兆光纤网络卡&#xff0c;支持万兆网络数据的收发和网络协议的定制设计。 …

weblogic JSP action的配置

action(如xxx.do&#xff09;可以在Java文件中通过注解的方式配置&#xff0c;也可以在web.xml中进行配置 在java文件中配置的场合 WebServlet(xxxx.do) 并实现支持的方法&#xff1a;doGet或doPost等 或者 WebServlet(xxxx.do) 并实现service方法 所有method的处理方法都会…

OpenHarmony音频和音乐编码格式—vorbis

简介 一种通用音频和音乐编码格式。 Vorbis编解码器规范属于公共领域。所有技术细节都已发布并记录&#xff0c;任何软件实体都可以充分利用该格式&#xff0c;而无需支付许可费、版税或专利问题。 下载安装 直接在OpenHarmony-SIG仓中搜索vorbis并下载。 使用说明 以OpenHa…

常用UI组件

一、文本组件 1.1 概述 Text为文本组件&#xff0c;用于显示文字内容 1.2 参数 Text组件的参数类型为string | Resource Entry Component struct Index {build() {Column({space : 50}) {Text(你好).fontSize(50)}.width(100%).height(100%).justifyContent(FlexAlign.Cent…

时序深入之CPR(Clock Pessimism Removal)详解

目录 一、CPR概念 二、CPR的计算 三、CPR的开启关闭 四、CPR为0 ​五、参考资料 一、CPR概念 在时序报告的目标时钟路径中&#xff0c;会有一行数据clock pesssimism&#xff0c;第一次见可能都会对这个概念感到疑惑 同样在每条时序路径的summary中&#xff0c;clock pat…

吴恩达机器学习笔记:第 7 周-12支持向量机(Support Vector Machines)12.4-12.6

目录 第 7 周 12、 支持向量机(Support Vector Machines)12.4 核函数 112.5 核函数 212.6 使用支持向量机 第 7 周 12、 支持向量机(Support Vector Machines) 12.4 核函数 1 回顾我们之前讨论过可以使用高级数的多项式模型来解决无法用直线进行分隔的分类 问题&#xff1a; …

CentOS7升级openssl

文章目录 一 系统环境二 操作步骤三 版本检查 一 系统环境 公司服务器等保要求&#xff0c;修复openssl的高危漏洞。 本机使用centos7.9系统&#xff0c;openssl版本是1.0.2k&#xff0c;计划升级到1.1.1q 在执行下列操作前&#xff0c;务必要打快照做好备份&#xff0c;以防升…