数据结构与算法
最好是一天一篇的稳定输出。
谁偷了我的月亮
高度近视不想敲代码的程序员。。。
展开
-
程序员常用十种算法(10)— 马踏棋盘算法
程序员常用十种算法(10)— 马踏棋盘算法1.马踏棋盘算法介绍1)马踏棋盘算法也被称为骑士周游问题;2)将马随机放在国际象棋的 8×8 棋盘 Board[0~7][0~7]的某个方格中,马按走棋规则(马走日字)进行移动.要求 每个方格只进入一次,走遍棋盘上全部 64 个方格。2.马踏棋盘游戏的代码实现1)马踏棋盘问题(骑士周游问题)实际上是图的深度优先搜索(DFS)的应用。2)如果使用回溯(就是深度优先搜索)来解决,假如马儿踏了 53 个点,如图:走到了第 53 个,坐标(1,0),发现已经走原创 2021-07-12 17:17:38 · 435 阅读 · 3 评论 -
程序员常用十种算法(9)— 弗洛伊德(Floyed)算法(最短路径问题)
程序员常用十种算法(9)— 弗洛伊德(Floyed)算法(最短路径问题)1.弗洛伊德(Floyed)算法介绍1)和 Dijkstra 算法一样,弗洛伊德(Floyd)算法也是一种用于寻找给定的加权图中顶点间最短路径的算法。该算法名称以创始人之一,1978 年图灵奖获得者,斯坦福大学计算机科学系教授罗伯特·弗洛伊德命名;2)弗洛伊德算法(Floyd)计算图中各个顶点之间的最短路径;3)迪杰特斯拉算法用于计算图中某一个顶点到其他顶点的最短路径;4)弗洛伊德算法 VS 迪杰斯特拉算法:迪杰斯特拉算法通过原创 2021-07-12 16:57:37 · 1679 阅读 · 0 评论 -
程序员常用十种算法(8)— 迪杰斯特拉(Dijkstra)算法(最短路径问题)
程序员常用十种算法(8)— 迪杰斯特拉(Dijkstra)算法(最短路径问题)1.迪杰斯特拉(Dijkstra)算法介绍迪杰斯特拉(Dijkstra)算法是典型最短路径算法,用于计算一个节点到其他节点的最短路径。它的主要特点是以起始点为中心向外层层扩展(广度优先搜索思想),直到扩展到终点为止。2.迪杰斯特拉(Dijkstra)算法过程1)设置出发顶点为 v,顶点集合 V{v1,v2,vi…},v 到 V 中各顶点的距离构成距离集合Dis,Dis{d1,d2,di…},Dis 集合记录着 v 到图中各原创 2021-07-12 15:34:21 · 437 阅读 · 2 评论 -
程序员常用十种算法(7)— 克鲁斯卡尔算法(公交站问题)
程序员常用十种算法(7)— 克鲁斯卡尔算法(公交站问题)1.克鲁斯卡尔算法介绍1)克鲁斯卡尔(Kruskal)算法,是用来求加权连通图的最小生成树的算法。2)基本思想:按照权值从小到大的顺序选择 n-1 条边,并保证这 n-1 条边不构成回路。3)具体做法:首先构造一个只含 n 个顶点的森林,然后依权值从小到大从连通网中选择边加入到森林中,并使森林中不产生回路,直至森林变成一棵树为止。*连通网的最小生成树: 在含有 n 个顶点的连通图中选择 n-1 条边,构成一棵极小连通子图,并使该连通子图中 n原创 2021-07-08 16:21:55 · 256 阅读 · 0 评论 -
程序员常用十种算法(6)— 普利姆算法(修路问题)
程序员常用十种算法(6)— 普利姆算法(修路问题)在介绍普利姆算法之前先介绍一下最小生成树。1. 最小生成树最小生成树(Minimum Cost Spanning Tree), 简称 MST。给定一个带权的无向连通图,如何选取一颗生成树,使树上所有边上权的总和为最小,这叫最小生成树:1)N个顶点,一定有N-1条边2)包含全部顶点3)N-1条边都在图中4)如下图例子所示5)求最小生成树的主要算法是普利姆算法和克鲁斯卡尔算法。2.普利姆算法介绍普利姆(Prim)算法求最小生成树,也就是在包含原创 2021-07-01 22:00:45 · 300 阅读 · 0 评论 -
程序员常用十种算法(5)— 贪心算法(集合覆盖问题)
程序员常用十种算法(5)— 贪心算法(集合覆盖问题)一、贪心算法的介绍(1)贪心算法是指在对任何问题进行求解时,在每一步选择中都采取最好或者最优(即最有利)的选择,从而希望能够导致结果是最好或者最优的算法。(2)贪婪算法所得到的结果不一定是最优的结果(有时候会是最优解),但是都是相对近似(接近)最优解的结果。二、贪心算法最佳应用-集合覆盖问题(1)问题描述:(2)思路分析:1)使用贪婪算法效率高,可以得到非常接近的解,选择策略上只需要覆盖全部地区的最小集合;2)遍历所有的广播电台,找到一个原创 2021-06-21 19:42:37 · 596 阅读 · 0 评论 -
程序员常用十种算法(4)— KMP算法(字符串匹配问题)
程序员常用十种算法(4)— KMP算法(字符串匹配问题)1.KMP算法介绍KMP是一个解决模式串在文本串是否出现过,如果出现过则返回最早出现位置的经典算法。KMP算法就是利用之前判断过的信息,通过一个next数组,保存模式串中前后最长公共子序列的长度,每次回溯时,通过next数组找到前面匹配过的位置,省去了大量的计算时间。2.KMP算法的最佳应用-字符串匹配问题(1)问题描述:(2)暴力匹配法:假设现在str1匹配到 i 位置,子串str2匹配到 j 位置,则有:1)如果当前字符匹配成功(即原创 2021-06-18 21:09:43 · 146 阅读 · 0 评论 -
程序员常用十种算法(3)— 动态规划算法(背包问题实现)
程序员常用十种算法(3)— 动态规划算法(背包问题实现)1.动态规划算法介绍:(1)动态规划(Dynamic Programming)算法的核心思想是:将大问题划分为小问题来解决,从而一步步获取最优解的处理算法。(2)动态规划算法与分治算法类似,其基本思想也是将待解决问题分解成若干个子问题,先求解子问题,然后从这些子问题的解得到原问题的解。(3)与分治算法不同的是,适合于用动态规划求解的问题,经分解得到的子问题往往不是相互独立的。(即下一个子阶段的求解是建立在上一个子阶段的解的基础上,进行进一步的求原创 2021-06-17 20:09:45 · 283 阅读 · 0 评论 -
程序员常用十种算法(2)— 分治算法(汉诺塔实现)
程序员常用十种算法(2)— 分治算法(汉诺塔实现)1.分治算法的介绍:分治算法就是把一个复杂的问题分成两个或者多个相同或者相似的小问题,再把子问题分成更小的子问题·····直到最后的子问题可以简单地直接求解,原问题的解即子问题的解的合并。2.可以解决的经典问题可以解决二分搜索、大整数乘法、合并排序、快排、棋盘覆盖、线性时间选择、最接近点对问题、循环赛日程表、汉诺塔等。(后面将以汉诺塔问题进行讲解)3.分治算法的基本步骤分治法在每一层递归上都有三个步骤:1)分解:将原问题分解为若干个规模较小,相原创 2021-06-11 22:01:35 · 265 阅读 · 3 评论 -
程序员常用十种算法(1)— 二分查找算法(非递归)
程序员常用十种算法(1)— 二分查找算法(非递归)之前的一篇博文有写过二分查找算法的递归实现,参考链接:二分查找算法的递归实现,二分查找算法只适用于从有序的数列中进行查找(比如数字和字母等),将数列排序后再进行查找,其时间复杂度为O(log2n)。代码实现:public class BinarySearchNoRecur { public static void main(String[] args) { int[] arr = {1,3,8,10,11,67,100};原创 2021-06-11 21:37:08 · 122 阅读 · 0 评论 -
从LeetCode魔术排列到LinkedList常用方法
从LeetCode魔术排列到LinkedList常用方法一、题目描述:二、解题思路:这个题目可以用暴力求解,但是时间复杂度太高了。看了LeetCode上各位大佬的解题思路,题目中的k值是确定的。明白这一点之后,就可以模仿这个过程了。至于k值为什么是确定的,可以参考下面链接,讲的很清楚。K值的确定k值实际就是第一步执行完之后的数组与target数组最长公共前缀。由于涉及到数组的删除与排序操作,所以用LinkedList比较好。后面将对LinkedList常用方法进行介绍。三、代码class原创 2021-05-30 16:37:06 · 99 阅读 · 0 评论 -
剑指offer--数组中只出现一次的两个数字
剑指offer–数组中只出现一次的两个数字一、题目描述二、解题思路(1)方法一:创建一个ArrayList,然后遍历数组,对于数组中每个元素进行判断,若List中已经存在,就去除掉原来存在的那个元素,如果list里面没有就往往里面添加上这个元素。最后遍历完整个数组后就剩下两个元素了。相关代码如下: ArrayList list = new ArrayList(); for (int i=0;i < array.length; i++){原创 2021-05-25 16:03:13 · 136 阅读 · 0 评论 -
从LeetCode的魔塔游戏到优先队列(PriorityQueue)
从LeetCode的魔塔游戏到优先队列(PriorityQueue)一、题目描述二、解题思路这个题目用到了优先队列,就很简单了。后面将会对优先队列进行详细的介绍。这个题目的解题思路分为两步:(1)求出所有元素的累加和,如果累加和小于1,直接返回-1;(2)如果累加和大于1,说明可以调整。则可以模拟这个游戏过程,将之前扣减的血量都放在优先队列中(小于0的值),每次快死之前取出堆顶元素(扣最多的血)给自己加上。三、代码如下class Solution { public int magi原创 2021-05-08 19:10:13 · 217 阅读 · 0 评论 -
LeetCode之最长回文子串
LeetCode之最长回文子串一、题目描述二、解题思路1.动态规划的解法:(1)思路:具体的细节可以看LeetCode官方的解题思路,在这里我给出一个宏观的思路。首先,所有的单个元素都是回文子串,之后就是开始枚举,从长度为2 的子串开始一直枚举到字符串的长度为止。在每一次枚举的时候需要dp[i][j]来表示s{i…j}是回文子串。时间复杂度:O(n^2)空间复杂度:O(n^2).(2)代码:class Solution { public String longestPalindro原创 2021-04-26 22:42:21 · 107 阅读 · 0 评论 -
剑指offer--字符串的排列
剑指offer–字符串的排列一、题目描述:二、思路解析:全排列的问题,最开始看到这个题目不知道怎么做,看了剑指offer上的方法:(a)把字符串分成两个部分:第一部分是字符串的第一个字符,第二部分是第一个字符后面的所有字符。之后求第二部分字符的全排列。(b)拿第一个字符和它后面的字符逐个交换。看了这个思路之后大致可以理解一下,但是还是不能去实现。之后又在牛客上看了一个小姐姐写的题解:假设输入为a、b、c那么其实排序的总数:fun(a,b,c)=a(fun(b,c))+ a和 b交换原创 2021-04-18 10:40:22 · 184 阅读 · 1 评论 -
剑指offer--连续子数组的最大和
剑指offer–连续子数组的最大和一、题目描述二、解题思路思路一:设置两个变量,一个变量保存累加值,一个变量保存最大值,当累加值小于等于0的时候,就更新累加值为当前值。代码如下:public class Solution { public int FindGreatestSumOfSubArray(int[] array) { if(array == null){ return 0; } int max = arra原创 2021-04-14 15:45:50 · 83 阅读 · 0 评论 -
剑指offer29-顺时针打印矩阵
剑指offer29-顺时针打印矩阵一.题目描述:二、解题思路:刚开始看到这个题目就觉得很麻烦,想的就是根据四个顶点来判断,但是还是好麻烦,就去看了看别人怎么做的,发现一个小姐姐的思路不错,将四个顶点简化为四条边界线,根据四条边界线来判断思路就比较清晰了。三、代码如下:import java.util.ArrayList;public class Solution { public ArrayList<Integer> printMatrix(int [][] matrix)原创 2021-04-13 22:19:08 · 69 阅读 · 0 评论 -
超实用的剔除法解决二维矩阵中的搜索问题
超实用的剔除法解决二维矩阵中的搜索问题一.问题描述二.解决思路这道题很多人都是将二维数组映射到一维数组中,然后利用二分查找的方法去解决。但是在本题中利用剔除法获取更简单,通过剔除行或列来进行定位。(1)首先判断边界条件;(2)之后通过每行的最后一个值来定位在哪一行;(3)确定行之后遍历这一行,查询这一行中是否有这个值。注: 对于大多数有关矩阵搜索的题目都可以这样做三、代码class Solution { public boolean searchMatrix(int[][] ma原创 2021-03-30 19:44:26 · 110 阅读 · 0 评论 -
LeetCode之旋转链表详解
LeetCode之旋转链表详解1.题目描述2.题目分析与解题思路本题考察的是链表的基本操作和取余的思想。(1)先判断边界条件;(2)循环遍历链表,计算链表的个数,同时放一个指针在链表最后一个结点;(3)根据K值和链表长度,取余来计算从哪里开始断链;(4)最后一个结点指向头结点再断链断链(注意这块的顺序)。3.代码/** * Definition for singly-linked list. * public class ListNode { * int val; *原创 2021-03-27 17:05:59 · 130 阅读 · 0 评论 -
时间复杂度最小的LeetCode两数相加题解
详解LeetCode两数相加1. 题目描述2.解题思路这个题目考察的就是链表+取余取整的操作,但是要注意细节。(1)首先考虑边界情况,两个链表有一个为null或者都为空的情况;(2)随便拿一条链表当返回链表,本题中我拿的是L1这条链表,每次两条链表相加都是对L1上的结点值进行更新;(3)用两个指针依次按顺序遍历每个结点,遍历的时候对应两个结点相加,然后进行取余和取整,循环结束的终点是只要有一条链表遍历完(最后一个结点单独处理);(4)循环完之后有三种情况:L1遍历完,L2遍历完,两条链表都遍历原创 2021-03-27 11:17:43 · 345 阅读 · 0 评论 -
平衡二叉树
平衡二叉树1.基本介绍(1)平衡二叉树也叫二叉搜索树又被称为AVL树,可以保证查询效率较高。(2)特点:它是一颗空树或它的左右两个子树的高度差的绝对值不超过1,并且左右两个子树都是一颗平衡二叉树。2.应用(1)左旋转给出一个数列{4, 3,6,5, 7, 8},创建出对应的平衡二叉树。思路如下(借助某教育机构的图):具体实现的代码块如下: //左旋转方法 private void leftRotate(){ //创建新的节点,值为当前结点的值原创 2021-03-05 22:16:09 · 98 阅读 · 0 评论 -
赫夫曼树
赫夫曼树1.概念:**赫夫曼树:**WPL最小的就是赫夫曼树,(WPL:weighted path length 树的带权路径长度即所有叶子结点带权路径长度之和,权值最大的结点距离根节点越近的二叉树才是最优二叉树)2.构建赫夫曼树的思路:(1)将每一个数据从小到大进行排序,每一个数据都是一个节点。每一个结点都可以看成是一颗最简单的二叉树。(2)每次取出根节点权值最小的两颗二叉树构建成一颗新树,新二叉树根节点的权值是前面两颗二叉树根节点的权值之和。(3)将新二叉树添加到数列中再次排序,不断重复(1原创 2020-11-06 19:54:47 · 88 阅读 · 0 评论 -
二叉树的应用(1):堆排序
二叉树的应用之堆排序的简单理解及代码实现一.堆排序的基本介绍1.堆排序是利用堆这种数据结构而设计的一种排序算法,堆排序是一种选择排序,它的最坏,最好,平均时间复杂度都为O(nlogn),同时是一种不稳定的排序。2.堆是具有以下性质的完全二叉树:每个节点的值都是大于或等于其左右孩子结点的值,称为大顶堆,没有要求结点的左孩子的值和右孩子的值的大小关系。每个节点的值都是小于或等于其左右孩子结点的值,称为小顶堆。3.一般升序采用大顶堆,降序采用小顶堆。二.堆排序的基本思想(大顶堆为例)1.将待排序的序列原创 2020-10-20 18:53:05 · 185 阅读 · 0 评论 -
二叉树(2)
二叉树(二):线索化二叉树的创建于遍历(附源码)**1.引进线索二叉树:**因为树结构中很多结点的左右指针没有用上,为了充分使用左右指针,所以引进线索二叉树。2.线索二叉树的创建过程(中序线索二叉树为例):(1)首先判断结点是否为空,若为空,退出递归(递归出口)(2)递归线索化左子树(3)线索化当前节点:a.如果当前结点的左指针为空,就把该结点的左指针指向前一个结点b.如果当前结点的右指针为空,就把前一个结点的右指针指向当前结点(!!!所以要先用一个指针指向前一个结点)(4)递归线索化右子树原创 2020-10-10 15:31:55 · 97 阅读 · 0 评论 -
二叉树
二叉树(一):树的基础知识以及相关的基础操作一.基础知识**1.引进树结构的原因:**结合了数组存储和链表存储的优点,能提高数据存储和读取的效率。**2.满二叉树:**该二叉树的所有叶子节点都在最后一层,并且节点总数=2^n-1,n为层数。**3.完全二叉树:**所有叶子节点都在最后一层或者倒数第二层,而且最后一层的叶子结点在左边连续,倒数第二层的叶子结点在右边连续。二,基本操作1.遍历:前序遍历:根左右中序遍历:左根右后续遍历:左右根2.查找指定的结点:前序遍历查找:(1)比较当前原创 2020-10-07 22:14:07 · 108 阅读 · 0 评论 -
查找算法(2):二分查找
查找算法(2):二分查找前提:查找的数组是一个有序数组。思路分析:1.首先确定数组的中间值的下标:mid = (left+right)/ 2;2.比较查找值findVal与arr[mid]的大小;3.若 findVal > arr[mid],说明需要查找的数在右边,需要向右递归查找;4.若 findVal < arr[mid],说明需要查找的数在左边,需要向左递归查找;5.若findVal==arr[mid],即找到,返回下标。递归出口:1.找到的时候结束递归2.递归完整个数原创 2020-10-02 22:38:04 · 95 阅读 · 0 评论 -
查找算法(1)
查找算法(1):线性查找算法线性查找算法就是最简单的从头到尾遍历整个数组,发现有相同的值就返回下标。```javapublic static int seqSearch(int[] arr, int value){ //逐一比对,发现有相同的值就返回下标 for (int i = 0; i < arr.length; i++) { if (arr[i]==value){ return i;原创 2020-10-02 22:02:03 · 67 阅读 · 0 评论