算法初步(julyedu网课整理)
date: 2018-11-19 13:41:29
updated: 2018-11-19 14:31:04
算法初步(julyedu网课整理)
1
O(1)
基本运算
O(logn)
二分查找 分治类问题基本上都有log
O(n)
线性查找
O(n²)
冒泡排序;选择排序
O(n的3次方)
Floyd最短路;普通矩阵乘法
O(nlogn)
归并排序和快速排序的期望复杂度;
基于比较排序的算法下界
原因:a1 a2 ...... an 等n个数 共有n!次种分布可能
比较一次 ai > aj 就筛选出来一半的结果 n!/ 2
比较第二次 ai > aj 就筛选出来一半结果的一半 n!/ 4 = n!/ 2 ²
做k次比较 n!/ 2的k次方
所以要经过多少次比较才能得到最后的排序结果?
n!/ 2的k次方 = 1
n! = 2的k次方
两边同时以2为底 log
log(n!) = k
因为log(n!) < log(n的n次方)
所以 k ≈ log(n的n次方) ≈ nlogn 下限最坏是nlogn
O(2的n次方)
暴力枚举所有子集
2
数组
数据在内存中连续存储:数组;非连续存储:链表、树;
vector(C++) 读写速率都是O(1)
当数组空间满了,vector会自动开辟一个两倍空间,丢弃原来的空间,将原始数据copy过来,有k个数则时间复杂度O(k)
3
算法优化的时候会从最内层循环开始,因为最内层会被一直循环执行
ex:一个数组中,某一子集的和最大
ans = -2147483647 作为判断的下界
int最小值 -2147483648 最大值2147483647
暴力枚举:三重循环
for i ← 1 to n
for j ← i to n
sum ← a[i] + ... + a[j]
ans ← max(ans,sum)
时间复杂度O(n的3次方) 附加空间复杂度O(1)
优化枚举:两重循环
a[2] + a[3]
a[2] + a[3] + a[4]
=> 不需要挨个加一遍,只需要把之前的结果保存再加后面的那一个数即可
for i ← 1 to n
sum ← 0
for j ← i to n
sum ← sum + a[j]
ans ← max(ans,sum)
时间复杂度O(n²) 附加空间复杂度O(1)
贪心算法:一重循环
sum ← 0; ans ← 0
for i ← 1 to n
sum = sum + a[i]
ans ← max(ans,sum)
if(sum < 0)
sum ← 0
时间复杂度O(n) 附加空间复杂度O(1)
if(sum < 0) sum ← 0 这部分是代码最终优化之后的结果,但是直接看的话不容易理解
再优化:求最大值问题转化成求最小值问题
问题是求 max(a[i]...a[j])
假设 s[i] = a[0] + ... + a[i]
那么问题就转化成 max(s[j] - s[i - 1])
对数组中的每一个j来说,s[j]是固定的,循环累加得到
那么问题就转化成 max(P - s[i - 1]),找到min(s[i - 1])
public int maxSubArray(int[] nums) {
int n = nums.length;
if(n == 0)
return 0;
int si = 0;
int sj = 0;
int minSi = 0;
int ans = Integer.MIN_VALUE;
for(int j = 0; j < n; ++j){
sj += nums[j];
if(si < minSi)
minSi = si;
if(sj - minSi > ans)
ans = sj - minSi;
si += nums[j];
}
return ans;
}
ex:[-2,1,-3,4,-1,2,1,-5,4]
| sj | minSi | ans | si | j |
|---|---|---|---|---|
| -2 | 0 | -2 | -2 | 0 |
| -1 | -2 | 1 | -1 | 1 |
| -4 | -2 | 1 | -4 | 2 |
| 0 | -4 | 4 | 0 | 3 |
| -1 | -4 | 4 | -1 | 4 |
| 1 | -4 | 5 | 1 | 5 |
| 2 | -4 | 5 | 2 | 6 |
sj不断累积
minSi取[0]...[j]中最小的那一个值
ans取sj - minSi中最大的那个一个值
优化:
sj += nums[j]
可以直接删掉,sj = si +nums[j]
public int maxSubArray(int[] nums) {
int n = nums.length;
if(n == 0)
return 0;
int si = 0;
int minSi = 0;
int ans = Integer.MIN_VALUE;
for(int j = 0; j < n; ++j){
if(si < minSi)
minSi = si;
if(si + nums[j] - minSi > ans)
ans = si + nums[j] - minSi;
si += nums[j];
}
return ans;
}
之后 if(si < minSi) 可以表示为 if(si - minSi < 0)
新建一个变量 sum 用来表示 si - minSi 进行变量替换,初始值为0
同时因为此时已经没有 minSi 了,所以对 si 的增量就相当于对 sum 的增量,所以 si += nums[j]就可以表示为 sum += nums[j]
public int maxSubArray(int[] nums) {
int n = nums.length;
if(n == 0)
return 0;
int sum = 0;
int ans = Integer.MIN_VALUE;
for(int j = 0; j < n; ++j){
if(sum < 0)
sum = 0;
if(sum + nums[j] > ans)
ans = sum + nums[j];
sum += nums[j];
}
return ans;
}
此时的代码和贪心法的一重循环是一致的
算法初步(julyedu网课整理)的更多相关文章
- 树和堆(julyedu网课整理)
date: 2018-12-05 16:59:15 updated: 2018-12-05 16:59:15 树和堆(julyedu网课整理) 1 定义 1.1 树的定义 它是由n(n>=1)个 ...
- 栈&队列&并查集&哈希表(julyedu网课整理)
date: 2018-11-25 08:31:30 updated: 2018-11-25 08:31:30 栈&队列&并查集&哈希表(julyedu网课整理) 栈和队列 1. ...
- 推荐书单(网课)-人生/编程/Python/机器学习-130本
目录 总计(130本) 一.在读 二.将读 三.已读 非专业书单(77本) 四.已读 专业书单(53本) 五.已看网课(8个) 六.在看网课 一个人如果抱着义务的意识去读书,便不了解读书的艺术.--林 ...
- 《计算机组成原理/CSAPP》网课总结(一)
现在是2022年4月17日晚10点,本月计划的网课<csapp讲解>视频课看到了第八章"异常"第三讲,视频讲的很好但更新很慢,暂时没有最新的讲解,所以先做一个简单总结. ...
- Linux内核学习期末总结(网课)
标签(空格分隔): 20135321余佳源 余佳源(原创作品转载请注明出处) <Linux内核分析> MOOC课程http://mooc.study.163.com/course/USTC ...
- php编写刷网课自助下单系统(第三方支付实例)
此项目是由于本人刚刚入门php且在校代刷网课而编写的,由于在上课时间不方便接单,故特意写一个自助下单系统来实现客户自助下单.本项目主要实现以下功能:1.用户下单2.用户支付3.用户通过账号查询订单4. ...
- python网课自动刷课程序-------selenium+chromedriver
python的强大之处就在于有许多已经写好的功能库提供,这些库强大且易用,对于写一些有特定功能的小程序十分方便. 现在就用pyhton的selenium+谷歌游览器写一个可以自动刷课的程序,以智慧树上 ...
- Scratch编程与高中数学算法初步
scratch编程与高中数学算法初步 一提到编程,大家可能觉得晦涩难懂,没有一定的英语和数学思维基础的人,一大串的编程代码让人望而步,何况是中小学生. Scratch是一款由麻省理工学院(MIT) ...
- 【原创】tarjan算法初步(强连通子图缩点)
[原创]tarjan算法初步(强连通子图缩点) tarjan算法的思路不是一般的绕!!(不过既然是求强连通子图这样的回路也就可以稍微原谅了..) 但是研究tarjan之前总得知道强连通分量是什么吧.. ...
随机推荐
- Gradle系列之Android Gradle高级配置
本篇文章主要在之前学习的基础上,从实际开发的角度学习如何对 Android Gradle 来进行自定义以满足不同的开发需求,下面是 Gradle 系列的几篇文章: Gradle系列之初识Gradle ...
- 使用Scrcpy实现电脑控制安卓手机
很多时候我们想要在电脑上使用一些手机软件,使用模拟器当然是一种选择,但是这些模拟器要不然不免费,要不然广告多不放心.Scrcpy是一个开源免费的软件,通过abd命令实现了安卓手机投屏和控制功能,并且支 ...
- switch-case 选择语句
0. 语句模型 Go 里的选择语句模型是这样的 switch 表达式 { case 表达式1: 代码块 case 表达式2: 代码块 case 表达式3: 代码块 case 表达式4: 代码块 cas ...
- selenium的文档API
你用WebDriver要做的第一件事就是指定一个链接,一般我们使用get方法: from selenium import webdriver from selenium.webdriver.commo ...
- jquery学习:
1.什么是jQuery jquery 全称 javaScript Query.是js的一个框架.本质上仍然是js. 2.jQuery的特点 支持各种主流的浏览器. 使用特别简单 拥有便捷的插件扩展机制 ...
- minium-微信小程序自动化框架-python,官方文档
minium文档 个人将其部署到了自己的服务器上,如有需要可以访问共同学习这个minium 用python来实现小程序自动化测试... 文档地址 http://49.232.203.244:3000/ ...
- Echarts山东省地图两级钻取、返回及济南合并莱芜地图
Echarts3.0+jQuery3.3.1 山东省地图中济南市需要注意下,莱芜市已经和济南市合并,地图数据来源于地图选择器,获取山东省地图信息及各地市地图信息(JSON格式) //山东地图(第一级地 ...
- Python-函数式编程-map reduce filter lambda 三元表达式 闭包
lambda 匿名函数,核心是作为算子,处理逻辑只有一行但具有函数的特性,核心用于函数式编程中 三元运算符 其实本质上是if分支的简化版,满足条件返回 if 前面的值,不满足条件返回 else后面的值 ...
- CISCO交换机STP实验(生成树协议)
目录 一.前言:生成树协议(STP) 二.CISCO交换机STP命令汇总 三.运用STP搭建简单拓扑 四.实战:STP综合实验 五.结语 一.前言:生成树协议(STP) 计算机网络中,我们为了减少网络 ...
- MySQL的简单实用 手把手教学
------------恢复内容开始------------ MySQL的使用 1.登陆数据库 打开terminal 在终端根文件目录下输入/usr/local/mysql/bin/mysql -u ...