1、反转数字
int reversee(int num){
int res=0;
int tmp=num;
while(num){
res*=10;
res+=num%10;
num/=10;
}
cout<<tmp<<" "<<res<<endl;
return res;
}
2、图形打印
(关键在于对循环嵌套的理解和关系表达式(一般找边界点的坐标变化 可以适当描点利用点斜式的运用)
画X(理解公式 注意关系 把图新放入二维中研究关系
杨辉三角
#include <iostream>
#include<iomanip>
using namespace std;
int a[50][50];
int main()
{
int n;
cin>>n;
a[1][1]=1;
for(int i=2;i<=n;i++){
for(int j=1;j<=i;j++){
a[i][j]=a[i-1][j]+a[i-1][j-1];
}
}
for(int i=1;i<=n;i++){
for(int j=1;j<=i;j++){
cout<<setw(3)<<a[i][j]<<" ";
}
cout<<endl;
}
}
打印空心一定要注意条件
#include <iostream>
#include<iomanip>
using namespace std;
int a[50][50];
int main()
{
//打印等边三角形
int n;
cin>>n;
for(int i=1;i<=n;i++){
//先是n-i个空格
for( int j=1;j<=n-i;j++)
cout<<" ";
//然后是2*i-1个*
//实心
// for(int j=1;j<=2*i-1;j++)
// cout<<"*";
//空心
for(int j=1;j<=2*i-1;j++){
//第一行 最后一行 打印的第一个 最后一个
if(i==1||i==n||j==1||j==2*i-1)
cout<<"*";
else cout<<" ";
}
cout<<endl;
}
//
}
打印图形一般利用斜率加点 用点斜式去构建关系
#include <iostream>
#include<iomanip>
using namespace std;
int a[50][50];
int main()
{
int n;
cin>>n;
for(int i=1;i<=2*n-1;i++){
if(i<n){
for(int j=1;j<=n+1-i;j++)
cout<<"*";
cout<<endl;
}
else if(i==n) cout<<"*"<<endl;
else if(i>n){
//k=1 (6,2)
//y-2=x-6
for(int j=1;j<=i-4;j++)
cout<<"*";
cout<<endl;
}
}
}
打印菱形
#include <iostream>
#include<iomanip>
using namespace std;
int a[50][50];
int main()
{
int n;
cin>>n;
for(int i=1;i<=2*n-1;i++){
if(i<n){
int j;
for(j=1;j<=n-i;j++)
cout<<" ";
for(int j=1;j<=2*i-1;j++)
cout<<"*";
cout<<endl;
}
else if(i==n){
for(int j=1;j<=2*i-1;j++)
cout<<"*";
cout<<endl;
}
else{
//利用坐标关系去求 因为*都在一条直线上
//(n+1,2) k=1
//y-2=x-(n+1)
//y=x-n+3
//空格
for(int j=1;j<i-n+1;j++)
cout<<" ";
//(n,2*n-1) k=-1
//y-(2*n-1)=-(x-n)
//y=-x+3n-1
// 起点到终点
for(int j=i-n+1;j<=-i+3*n-1;j++)
cout<<"*";
cout<<endl;
}
}
}
数字菱形(未完成)
#include <iostream>
#include<iomanip>
using namespace std;
int a[50][50];
int main()
{
int n;
cin>>n;
for(int i=1;i<=2*n-1;i++){
if(i<n){
int j;
for(j=1;j<=n-i;j++)
cout<<" ";
int num=1;
for(int j=1;j<=2*i-1;j++){
if(j<i)
cout<<num++;
else if(j==i)
cout<<num;
else{
cout<<(--num);
}
}
cout<<endl;
}
else if(i==n){
int num=1;
for(int j=1;j<=2*i-1;j++){
if(j<i)
cout<<num++;
else if(j==i)
cout<<num;
else{
cout<<(--num);
}
}
cout<<endl;
}
else{
for(int j=1;j<i-n+1;j++)
cout<<" ";
int num=1;
//sb了 只需判断列y与中心就行 j这里是坐标
for(int j=i-n+1;j<=-i+3*n-1;j++){
if(j<n){
cout<<num++;
}
else if(j==n)
cout<<num;
else cout<<--num;
}
cout<<endl;
}
}
}
3、排序
自定义排序
注意cmp比的是数据类型
#include<bits/stdc++.h>
using namespace std;
//typedef pair<int,int> PII;
//bool cmp(PII &a,PII &b){
//
// if(a.second!=b.second)
// return a.second<b.second;
// else return a.first<b.first;
//}
class Person{
public:
string name;
int age;
Person(string na,int ag):name(na),age(ag){}
//法二 重载小于运算符
bool operator <( const Person &b){
if(this->age==b.age)
return this->name<b.name;
else return this->age<b.age;
}
};
//法一 自己定义函数
//bool cmp(Person x,Person y)
//{
// if(x.name==y.name)
// return x.age<y.age;
// else return x.name<y.name;
//}
int main()
{
// vector<PII>stu;
// int n;
// cin>>n;
//
// for(int i=1;i<=n;i++)
// {
// int p,q;
// cin>>p>>q;
// //这里pair类型的操作 要会
// stu.push_back({p,q});
// }
// sort(stu.begin(),stu.end(),cmp);
//
// for(auto i:stu)
// cout<<i.first<<" "<<i.second<<endl;
int n;
cin>>n;
vector<Person>num;
for(int i=0;i<n;i++)
{
string name;
int age;
cin>>name>>age;
Person p(name,age);
num.push_back(p);
}
sort(num.begin(),num.end());
for(auto i:num)
{
cout<<i.name<<" "<<i.age<<endl;
}
}
stl的用法解题
一些遍历时的注意事项 例如 for循环时 用迭代器begin end 还是 size
find函数返回的是迭代器 没找到返回end
#include<bits/stdc++.h>
using namespace std;
int main()
{
string ch;
getline(cin,ch);
unordered_set<char>sh;
for(int i=0;i<ch.size();i++)
{
if(sh.find(ch[i])==sh.end())
{
sh.insert(ch[i]);
vector<int>vc;
vc.clear();
vc.push_back(i);
for(int j=i+1;j<ch.size();j++)
{
if(ch[j]==ch[i])
vc.push_back(j);
}
// cout<<vc.size()<<endl;
if(vc.size()!=1)
for(int k=0;k!=vc.size();k++)
{
if(k!=vc.size()-1)
cout<<ch[i]<<":"<<vc[k]<<",";
else cout<<ch[i]<<":"<<vc[k]<<endl;;
}
}
}
}
字符串的处理
补充遗忘的一个知识点:gets()函数
然后就是还有getline gets 都会将回车从缓冲区拿走
一、字符串映射成数字 0~25
j=((str[i]-'A')-5)%26;
二、字符串的ascill码再0-127之间 可以开辟一个数字进行存储
三、用map存储 通过索引找
unordered_map<char,int>mp;
for(int i=0;i<ch.size();i++)
{
mp[ch[i]]++;
}
栈的应用
核心思想 定义两个栈 然后数字进栈 运算符比较优先级 栈顶优先级大于等于当前字符串优先级 进行运算
double eval()
{
double a=num.top();
num.pop();
double b=num.top();
num.pop();
char ch=op.top();
op.pop();
if(ch=='+')
num.push(a+b) ;
if(ch=='-')
num.push(a-b);
if(ch=='*')
num.push(a*b);
if(ch=='/')
num.push(a/b);
}
unordered_map<char,int> h {{'+',1},{'-',1},{'*',2},{'/',2}};
进制转换
核心思想就是 先取模 再除 有时要用字符串进行处理 加入高精度
#include<bits/stdc++.h>
using namespace std;
//高精度除法
string divede(string ch)
{
vector<int>num;
int res=0;
int yu=0;
//类似高精度处理 记住这么弄
for(int i=0;i<ch.size();i++)
{
int tmp=yu*10+ch[i]-'0';
ch[i]=tmp/2+'0';
yu=tmp%2;
}
// int pos=0;
// while(ch[pos]=='0')
// pos++;
// 123456 pos=2 size=6
reverse(ch.begin(),ch.end());
while(ch.back()=='0')
ch.pop_back();
reverse(ch.begin(),ch.end());
return ch;
}
int main()
{
string ch;
while(getline(cin,ch))
{
vector<int>num;
num.clear();
while(ch.size())
{
//核心思想
int last=ch[ch.size()-1]-'0';
num.push_back(last%2);
ch=divede(ch);
}
for(int i=num.size()-1;i>=0;i--)
cout<<num[i];
}
}
NM的进制转换
#include<bits/stdc++.h>
using namespace std;
int change(char ch)
{
if(ch>='0'&&ch<='9')
return ch-'0';
else return ch-'A'+10;
}
int main()
{
int M,N;
string x;
cin>>M>>N;
getchar();
cin>>x;
//转换成十进制
int res=0;
for(int i=0;i<x.size();i++)
{
res=res*M+change(x[i]);
}
//十进制转换成N进制
vector<int>num;
while(res)
{
num.push_back(res%N);
res/=N;
}
for(int i=num.size()-1;i>=0;i--)
if(num[i]>=9&&num[i]<=36)
cout<<(char)(num[i]-10+'A');
else cout<<num[i];
}
筛质数
记住埃筛就行 然后分解质因子
约数
未完成(约数之和)
最大公约数
int gcd(int a,int b))
{
return b?gcd(b,a%b):a;
}
a*b=最大公约数*最小公倍数 因此可以通过最大公约数求最小公倍数
矩阵乘法
不知道哪里错了 未解决
#include<bits/stdc++.h>
using namespace std;
const int max_len=100;
void fun(int marxi_1[max_len][max_len] , int m, int n,int marxi_2[max_len][max_len],int x,int y){
int marxi_ans[max_len][max_len];
memset(marxi_ans,0,sizeof(marxi_ans));
for(int i=1;i<=m;i++)
{
for(int j=1;j<=y;j++)
{
for(int k=1;k<=n;k++)
marxi_ans[i][j]+=marxi_1[i][k]*marxi_2[k][y];
}
}
for(int i=1;i<=m;i++)
{
for(int j=1;j<=y;j++)
cout<<marxi_ans[i][j]<<" ";
cout<<endl;
}
}
int main()
{
int marxi_1[max_len][max_len];
int marxi_2[max_len][max_len];
memset(marxi_1,0,sizeof(marxi_1));
memset(marxi_2,0,sizeof(marxi_2));
int m,n;
cin>>m>>n;
int x,y;
cin>>x>>y;
for(int i=1;i<=m;i++)
for(int j=1;j<=n;j++)
cin>>marxi_1[i][j];
for(int i=1;i<=x;i++)
for(int j=1;j<=y;j++)
cin>>marxi_2[i][j];
fun(marxi_1,m,n,marxi_2,x,y);
}
矩阵的幂 思想是矩阵乘法+快速幂
高精度
没有背模板 到时看acwing的
递归 汉诺塔
将问题抽象化 看局部 找出口
#include <iostream>
using namespace std;
int num=0;
void hannota(char start,char tmp,char ended,int n)
{
if(n==1)
{
cout<<start<<"->"<<ended<<endl;
num++;
return;
}
else
{
hannota(start,ended,tmp,n-1);
hannota(start,tmp,ended,1);
hannota(tmp,start,ended,n-1);
}
}
void hannota_num(char start,char tmp,char ended,int n)
{
if(n==1)
{
num++;
return;
}
else
{
hannota(start,ended,tmp,n-1);
hannota(start,tmp,ended,1);
hannota(tmp,start,ended,n-1);
}
}
int main()
{
int n;
cin>>n;
hannota_num('A','B','C',n);
cout<<num<<endl;
hannota('A','B','C',n);
}
#include<bits/stdc++.h>
using namespace std;
void hannuota(int x,int y,int z,int n){
//如果只是最后一个 打印
if(n==1){
printf("%d--->%d\n",x,z);
}
else{
//将n-1个看成一个整体 移到过渡点
hannuota(x,z,y,n-1);
//打印最底层的
printf("%d--->%d\n",x,z);
//然后将中间的过渡整体移到目标位置
hannuota(y,x,z,n-1);
}
}
int main()
{
//汉诺塔问题
int n;
cin>>n;
//从1-->3经过 借助2
hannuota(1,2,3,n);
}
BFS
#include <iostream>
#include<vector>
#include<set>
#include<queue>
using namespace std;
const int N=210;
int a[N][N];
bool visit[N][N];
typedef pair<int,int>PII;
int n,m;
int dx[4]={0,0,-1,1};
int dy[4]={-1,1,0,0};
int bfs(int i,int j)
{
queue<PII>que;
que.push({i,j});
visit[i][j]=true;
int sum=0;
int flag=0;
while(!que.empty())
{
auto tmp=que.front();
que.pop();
int x=tmp.first,y=tmp.second;
if(a[x][y]==-1)
{
sum=-1;
flag=1;
}
else
{
sum+=a[x][y];
}
for(int i=0;i<4;i++)
{
int next_x=x+dx[i];
int next_y=y+dy[i];
if(next_x<=n&&next_x>0&&next_y<=m&&next_y>0&&a[next_x][next_y]&&!visit[next_x][next_y])
{
que.push({next_x,next_y});
visit[next_x][next_y]=true;
}
}
}
if(flag==1)
return -1;
return sum;
}
int main()
{
cin>>n>>m;
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
cin>>a[i][j];
int ans=0;
for(int i=1;i<=n;i++)
{
for(int j=1;j<=m;j++)
{
if(a[i][j]&&!visit[i][j])
{
ans=max(bfs(i,j),ans);
}
}
}
cout<<ans<<endl;
}
string转int double(stoi stod)
进制 八进制 oct 十进制 dec 十六进制 hex
组合数(打表)
void init()
{
for(int i=0;i<N;i++)
for(int j=0;j<N;j++)
{
if(j==0||j==i)
c[i][j]=1;
else
{
c[i][j]=c[i-1][j-1]+c[i-1][j];
}
}
}