Acwing算法基础

Acwing算法基础

课下:

1理解思想

2背写代码模板

3课后题目 —检验掌握程度

1.1排序

1)快速排序

​ 算法思想:

​ 1交换排序。设置两个分别指向首和尾的指针 并设置一个中间值(一般设置队首),将左指针不断向右找,知道l < pivot 右指针向左找, 直到 r > pivot.然后交换.递归 直到只有一个数据或者无数据。

#include<iostream>`
`using namespace std;`

`void quick_sort(int q[] , int l, int r){`
	`if( l >= r)return ;`
	`int i= l - 1 , j = r + 1 , povit = q[l];`
	`while(i < j){`
		`do i++; while(q[i] < povit);`
		`do j--; while(q[j] > povit);`
		`if(i < j) swap(q[i],q[j]);`
	`}` 
	`quick_sort(q, l, j);`
	`quick_sort(q, j+1, r);`
`}`
`int main()`
`{`
	`int n;`
	`cin>>n;`
	`int str[n];`
	`for(int i=0;i<n;i++){`
	`cin>>str[i];`
	`}`
	`quick_sort(str,0,n-1);`
	`for(int i=0;i<n;i++){`
		`cout<<str[i]<<" ";`
	`}`
	`cout<<endl;`
	`return 0;`
 `}` 

2)归并排序

​ 算法思想:双指针 、 分治 、递归

​ 1)以中间点mid 为分界点

​ 2)递归排序Left Right

​ 3)将左右两个排序后的数组合二为一

#include<bits/stdc++.h>
using namespace std;
int t;
void merge_sort(int q[], int tmp[] ,int left, int right,int t)
{
	//只有一个元素不用继续分 
	if(left >= right)return ;
	//找到中间值
	int mid = (left + right)/2; 
	//对左边划分
	merge_sort(q,tmp,left,mid,t);
	//对右边划分
	merge_sort(q,tmp,mid+1,right,t);
	
	//进行归并排序
	int l_pos = left,r_pos = mid + 1, pos = left;
	//将左右两个部分合二为一
	while(l_pos <= mid&&r_pos <= right){
	if(q[l_pos] < q[r_pos])tmp[pos++] = q[l_pos++];	
	else tmp[pos++] = q[r_pos++];
	}
	//左边有剩余元素
	while(l_pos <= mid ) tmp[pos++] = q[l_pos++];
	//右边右元素 
	while(r_pos <= right ) tmp[pos++] = q[r_pos++];
		t=left;
	 while(left <= right){
//	 	if(tmp[left]==tmp[left+1]){
//	 		q[t] = tmp[left];
//	 		left++;
//		 }else{
		 	q[t] = tmp[left];
	 		left++;t++;
//		 }	
		 } 
	 } 
int main()
{
	/*
		1 - 1000 的 数据用数组存储
		 
	*/
	int str[10100],tmp[10100];
	int n,t=0;
	cin>>n;
	for(int i=0;i<n;i++){
		cin>>str[i];
	}
	merge_sort(str,tmp,0,n-1,t);
//	cout<<t<<endl;
	for(int i=0;i<n;i++){
		cout<<str[i]<<" ";
	}
	cout<<endl;
 } 

1.2二分

​ 整数二分

​ 浮点数二分

1.3高精度

​ 高精度加法 A(length(A)<1.0e9) + B(length(A)<1.0e9) = C

​ 解法 1)将A和B逆序存储在动态数组里(vector<>)

​ 2)将两个数据相加的结果存储在容器C里

#include<iostream>
#include<vector>

using namespace std;
//实现A+B 
vector<int>  add(vector<int>&A,vector<int>&B)
{
	 vector<int>C;
	 

	 if(A.size()-1 < B.size()-1 )return add(B,A); 
	 
	 int t = 0;
	 for(int i = 0; i < A.size(); i++)
	 {
	 	t += A[i];
	 	if(i < B.size())	t += B[i];
	 	C.push_back(t%10);
	 	t = t/10;
	 }
	 
	 if(t) C.push_back(1);
	 return C;

 } 

int main()
{
	//定义两个动态数组 
	vector<int>A,B;
	

	string a,b;
				 //string 定义的字符串 可直接当字符数组用 
				//将输入的数据逆序存储在A\B数组里
	cin>>a>>b;//a = "123456"
	
	for(int i = a.size() - 1; i >= 0; i--)A.push_back(a[i] - '0');
	for(int i = b.size() - 1; i >= 0; i--)B.push_back(b[i] - '0');
	
	//auto(自动,automatic)是存储类型标识符,表明变量"自动"具有本地范围,
	//块范围的变量声明(如for循环体内的变量声明)默认为auto存储类型。
	vector<int > C = add(A,B); //A = [6,5,4,3,2,1];
	
	 for(int i= C.size()-1; i >= 0; i--)
	 {
	 	cout<<C[i];
	 }

}

​ 高精度减法 A - B =C

​ 解法: 1)将A、B逆序存储到动态数组vector里

​ 2)判断 A 与 B 的 值谁大 较大的在前

​ 3)编写减法函数 : 如果 A[i] < b[i] t = -1;

#include<bits/stdc++.h>
using namespace std;
//判断A 与 B 的关系
bool cmp(vector<int> A , vector<int> B)
{
	if(A.size() != B.size())return A.size() > B.size();
	
	for(int i = 0; i < A.size(); i++)
	{
		if(A[i] != B[i]) return A[i] > B[i] ;
	}
 } 
//A - B
vector<int> subtraction(vector<int> &A,vector<int> &B)
{
	vector<int> C;
	//A - B
	int t = 0;
	/*
		 A > B  200 - 50 = 150;
	*/
	for(int i = 0; i < A.size() ; i++)
	{
		t = A[i] - t;
		if(i < B.size()) t -= B[i] ;
		C.push_back((t+10)%10);
		if(t<0)t = 1;
		else t = 0;
	} 
	//会出现003的现象
	while(C.size() > 1 && C.back()==0 ) C.pop_back();
	 return C;
}
int main()
{
	string a,b;//a = "12345" b=" 66 "
	cin>>a>>b;
	vector<int> A,B;
	//将A、B逆序存储到动态数组A,B里
	 for(int i = a.size() - 1; i >= 0; i--)A.push_back(a[i] - '0');
	 for(int i = b.size() - 1; i >= 0; i--)B.push_back(b[i] - '0');
	 //将较大的数放在减数位置
	 if(cmp(A,B)) 
	 {
	 	vector<int> C = subtraction(A , B);
	 	for(int i = C.size() -1; i>=0; i--)cout<<C[i];
	 }
	 else	
	 {
	 vector<int> C = subtraction(B , A)	;
	 cout<<"-";
	 for(int i = C.size() -1; i>=0; i--)cout<<C[i];
	 } 
	return 0;
}

高精度乘法 A * b = C

​ 思想:从 高精度A 的第一位开始,乘b, 加上进位t ,

​ 模10放进数组,直到t = 0, i = A.size

#include<bits/stdc++.h>
using namespace std;
//乘法 t负责进位 
vector<int> mul(vector<int> &A, int b)
{
	vector<int> C;
	int t = 0;
	for(int i = 0; i < A.size() || t; i++)
	{
		if(i < A.size()) t += A[i] * b;
		C.push_back(t % 10);
		t /= 10;
	}
	while(C.size() > 1 && C.back() == 0)C.pop_back();
	return C;
}
int main()
{
	//乘法 A * b
	string a ;
	int b;
	cin>>a>>b;
	vector<int> A;
	for(int i = a.size() - 1; i >= 0 ; i--)A.push_back(a[i] - '0');
	vector<int> C = mul(A , b);
	for(int i = C.size() - 1; i >= 0; i--)cout<<C[i];
	return 0; 
}

​ 高精度除低精度 A / b = C

​ 思想:

1.4前缀和与差分

前缀和

一维前缀和 —— 模板题 AcWing 795. 前缀和
S[i] = a[1] + a[2] + … a[i]
a[l] + … + a[r] = S[r] - S[l - 1]
二维前缀和 —— 模板题 AcWing 796. 子矩阵的和
S[i, j] = 第i行j列格子左上部分所有元素的和
以(x1, y1)为左上角,(x2, y2)为右下角的子矩阵的和为:
S[x2, y2] - S[x1 - 1, y2] - S[x2, y1 - 1] + S[x1 - 1, y1 - 1]

一维差分

​		在a[L,R] + C

​		b[l] += c;

​		b[r+1] -= c; 

二维差分

insert(int x1, int y1, int x2, int y2, int c)
{
		b[x][y] += c;
		b[x1][y2+1] -= c;
		b[x2+1][y1] -= c;
		b[x2+1][y2+1] += c;
}

1.5双指针算法

for (int i = 0, j = 0; i < n; i ++ )
{
    while (j < i && check(i, j)) j ++ ;

    // 具体问题的逻辑
}
常见问题分类:
    (1) 对于一个序列,用两个指针维护一段区间
    (2) 对于两个序列,维护某种次序,比如归并排序中合并两个有序序列的操作
class Solution {
public:
    int longestSubstringWithoutDuplication(string s) {
        int d[1010];
        int res = 0;
        for(int i = 0 , j = 0; i < s.length(); i++)
        {
            d[s[i] - 'a']++;
            //从 j 到 i 是否有相同的字符
            while(d[s[i] - 'a'] > 1)
            {
                d[s[j] - 'a']--;
                j++;
            }
            res = max(res,i-j+1);
        }
      return res;  
    }
};
  • 10
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: acwing算法基础课是一门针对算法学习的在线课程,在这门课程中,学生可以系统地学习和掌握算法基础知识,提高编程水平。为了方便学生学习,acwing提供了网盘服务。 acwing算法基础课网盘是一个用于存储课程资源的平台。通过这个网盘,学生可以下载课程讲义、代码模板以及补充材料等。这些资源都经过精心整理,供学生们参考和学习。 网盘中的资源是按照课程章节进行分类的,学生可以根据自己的学习需要,选择性地下载所需的资料。同时,网盘还提供了搜索功能,方便学生快速定位和获取所需资料。 acwing算法基础课网盘的使用对于学生们的学习非常有帮助。通过下载和学习这些资源,学生们可以更好地理解课程内容,加深对算法的理解。此外,学生们还可以通过研究代码模板,学习优秀的编程思想和技巧,提高自己的编程能力。 总之,acwing算法基础课网盘是一项非常便利和实用的服务,为学生们提供了更加全面和深入的学习资源,帮助他们更好地掌握和运用算法知识。 ### 回答2: acwing算法基础课是一门优质的算法学习资源,其中的课程内容丰富多样,涵盖了算法基础知识、数据结构、动态规划、图论等等。很多学习者都认为这门课程对他们的算法学习有很大的帮助。 网盘是指以网络为媒介,提供文件存储和下载服务的云存储平台。acwing算法基础课也提供了网盘服务,方便学习者下载课程资料并进行学习。 通过acwing算法基础课网盘,学习者可以方便地获取到课程的各种学习资料,包括讲义、习题集、代码示例等。这些资料可以帮助学习者更好地理解和掌握课程的内容。此外,网盘还提供了上传和分享功能,学习者可以将自己的学习心得、代码等资料分享给其他学习者,促进学习者之间的互相学习和交流。 acwing算法基础课网盘的优点不仅仅是方便快捷的下载和分享功能,还包括安全可靠的存储环境。学习者可以放心地将自己的学习资料上传到网盘进行备份,减少数据丢失的风险。同时,网盘还提供了多种存储空间容量的选择,满足学习者不同的需求。 总的来说,acwing算法基础课网盘为学习者提供了方便、安全和多样化的学习资源下载和分享服务,为学习者的算法学习和进步提供了有力的支持。如果你对算法感兴趣,我推荐你去尝试一下这门精彩的课程!

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值