zoukankan      html  css  js  c++  java
  • CSP 2019 RP++

    读入:(转自:chuyds's Blog

    法一:

    while(scanf("%d",&a)!=EOF)
    

    法二:

    while(cin>>n)
    

    法三:

    while(~scanf("%d",&a))
    

    1.最小生成树

    只会Kruskal w

    #include<bits/stdc++.h>
    
    using namespace std;
    
    inline int read(){
    	int ans=0;
    	char last=' ',ch=getchar();
    	while(ch>'9'||ch<'0') last=ch,ch=getchar();
    	while(ch>='0'&&ch<='9') ans=(ans<<1)+(ans<<3)+ch-'0',ch=getchar();
    	if(last=='-') ans=-ans;
    	return ans;
    }
    
    int n,m;
    int fa[5010];
    struct node{
    	int u,v,w;
    }e[200010];
    
    bool cmp(node a,node b) {
    	return a.w<b.w;
    }
    
    int find(int x){
    	if(fa[x]!=x) fa[x]=find(fa[x]);
    	return fa[x];
    }
    
    int main(){
    	n=read();
    	m=read();
    	for(int i=1;i<=m;i++) {
    		e[i].u=read();
    		e[i].v=read();
    		e[i].w=read();
    	}
    	sort(e+1,e+m+1,cmp);
    	int ans=0;
    	for(int i=1;i<=n;i++) fa[i]=i;
    	for(int i=1,u,v,fu,fv;i<=m;i++) {
    		u=e[i].u;
    		v=e[i].v;
    		fu=find(u);
    		fv=find(v);
    		if(fu==fv) continue;
    		fa[fu]=fv;
    		ans+=e[i].w;
    	}
    	printf("%d",ans);
    	return 0;
    }
    

    2.单源最短路

    dijkstra

    #include<bits/stdc++.h>
    #define pa pair<int,int>
    
    using namespace std;
    
    inline int read(){
        int ans=0;
        char last=' ',ch=getchar();
        while(ch>'9'||ch<'0') last=ch,ch=getchar();
        while(ch>='0'&&ch<='9') ans=(ans<<1)+(ans<<3)+ch-'0',ch=getchar();
        if(last=='-') ans=-ans;
        return ans;
    }
    const int mxn=100010;
    
    int n,m,s;
    int head[mxn],ecnt;
    struct node {
        int to,dis,nxt;
    }e[mxn<<1];
    
    void add(int from,int to,int dis){
        ++ecnt;
        e[ecnt].nxt=head[from];
        e[ecnt].to=to;
        e[ecnt].dis=dis;
        head[from]=ecnt;
    }
    
    int dis[mxn];
    bool vis[mxn];
    priority_queue<pa,vector<pa>,greater<pa> > q;
    void dij(int s){
        dis[s]=0;
        q.push(make_pair(dis[s],s));
        while(!q.empty()){
            int u=q.top().second;
            q.pop();
            if(vis[u]) continue;
            vis[u]=1;
            for(int i=head[u],v;i;i=e[i].nxt){
                v=e[i].to;
                if(dis[v]>dis[u]+e[i].dis){
                    dis[v]=dis[u]+e[i].dis;
                    q.push(make_pair(dis[v],v));
                }
            }
        }
    }
    
    int main(){
        n=read();
        m=read();
        s=read();
        memset(dis,0x3f,sizeof(dis));
        for(int i=1,u,v,w;i<=m;i++){
            u=read();
            v=read();
            w=read();
            add(u,v,w);
        }
        dij(s);
        for(int i=1;i<=n;i++) printf("%d ",dis[i]);
        return 0;
    }
    

    spfa

    #include<bits/stdc++.h>
    
    using namespace std;
    
    inline int read(){
        int ans=0;
        char last=' ',ch=getchar();
        while(ch>'9'||ch<'0') last=ch,ch=getchar();
        while(ch>='0'&&ch<='9') ans=(ans<<1)+(ans<<3)+ch-'0',ch=getchar();
        if(last=='-') ans=-ans;
        return ans;
    }
    const int mxn=100010;
    
    int n,m,s;
    int head[mxn],ecnt;
    struct node {
        int to,dis,nxt;
    }e[mxn<<3];
    
    void add(int from,int to,int dis){
        ++ecnt;
        e[ecnt].nxt=head[from];
        e[ecnt].to=to;
        e[ecnt].dis=dis;
        head[from]=ecnt;
    }
    int dis[mxn];
    bool vis[mxn];
    queue<int> Q;
    
    void spfa(){
    	
    	Q.push(s);
    	for(int i=1;i<=n;i++) dis[i]=2147483647,vis[i]=0;
    	vis[s]=1;dis[s]=0;
    	while(!Q.empty()) {
    		int u=Q.front();
    		Q.pop();
    		vis[u]=0;
    		for(int i=head[u],v;i;i=e[i].nxt) {
    			v=e[i].to;
    			if(dis[v]>dis[u]+e[i].dis) {
    				dis[v]=dis[u]+e[i].dis;
    				if(!vis[v]) Q.push(v),vis[v]=1;
    			}
    		}
    	}
    }
    
    int main(){
        n=read();
        m=read();
        s=read();
        
        for(int i=1,u,v,w;i<=m;i++){
            u=read();
            v=read();
            w=read();
            add(u,v,w);
        }
        spfa();
        for(int i=1;i<=n;i++) printf("%d ",dis[i]);
        return 0;
    }
    

    3.tarjan

    void tarjan(int u) {
    	dfn[u]=low[u]=++tim;
    	vis[u]=1;
    	s[top++]=u;
    	for(int i=head[u],v;i;i=e[i].nxt) {
    		v=e[i].to;
    		if(!dfn[v]) {
    			tarjan(v);
    			low[u]=min(low[v],low[u]);
    		} else 
    			if(vis[v]) 
    				low[u]=min(dfn[v],low[u]);
    	}
    	if(dfn[u]==low[u]){
    		++scc_cnt;
    		while(s[top]!=u){
    			top--;
    			vis[s[top]]=0;
    			scc[s[top]]=scc_cnt;
    			cnt[scc_cnt]++;
    		}
    	}
    }
    

    4.kmp

    #include<bits/stdc++.h>
    
    using namespace std;
    
    char a[mxn],b[mxn];
    int lena,lenb;
    
    int p[mxn];
    
    void ych(){
        p[1]=0;
        int j=0;
        for(int i=1;i<lenb;i++) {
            while(j>0&&b[j+1]!=b[i+1]) j=p[j];
            if(b[j+1]==b[i+1]) j++;
            p[i+1]=j;
        }
    }
    
    void kmp(){
        int j=0;
        for(int i=0;i<lena;i++) {
            while(j>0&&b[j+1]!=a[i+1]) j=p[j];
            if(b[j+1]==a[i+1]) j++;
            if(j==lenb) {
                printf("%d
    ",i+1-lenb+1);
                j=p[j];
            }
        }
    }
    
    int main(){
        scanf("%s%s",a+1,b+1);
        lena=strlen(a+1);
        lenb=strlen(b+1);
        ych();
        kmp();
        return 0;
    }
    

    trie树:

    #include<bits/stdc++.h>
    
    using namespace std;
    
    int n,m,tot=1; 
    char word[55];
    int trie[500011][27];
    int vis[500011];
    
    void insert(char *s,int rt) {
    	for(int i=0;i<strlen(s);i++) {
    		int x=s[i]-'0';
    		if(trie[rt][x]==0) trie[rt][x]=++tot;
    		rt=trie[rt][x];
    	}
    	vis[rt]=1;
    }
    
    int search(char *s,int rt) {
    	for(int i=0;i<strlen(s);i++) {
    		int x=s[i]-'0';
    		if(trie[rt][x]==0) return 0;
    		rt=trie[rt][x];
    	}
    	if(vis[rt]==0) return 0;
    	if(vis[rt]==1) { 
    		vis[rt]=2;
    		return 1;
    	}
    	if(vis[rt]==2)
    		return 2;
    }
    
    int main() {
    	scanf("%d",&n);
    	for(int i=1;i<=n;i++) {
    		scanf("%s",word);
    		insert(word,1);
    	}
    	scanf("%d",&m);
    	for(int i=1;i<=m;i++) {
    		scanf("%s",word);
    		int k=search(word,1);
    		if(!k) printf("WRONG
    ");
    		else {
    			if(k==1) 	
    				printf("OK
    ");
    			else 
    				printf("REPEAT
    ");
    		}
    	} 
    	return 0;
    }
    

    5.线性筛

    #include<bits/stdc++.h>
    
    using namespace std;
    
    const int mxn=100010;
    
    int n;
    bool is[mxn];
    int pri[mxn],cnt;
    
    int main(){
        scanf("%d",&n);
        for(int i=2;i<=n;i++) {
            if(!is[i]) pri[++cnt]=i;
            for(int j=1;j<=cnt&&pri[j]*i<=n;j++) {
                is[i*pri[j]]=1;
                if(i%pri[j]==0) break;
            }
        }
        for(int i=1;i<=cnt;i++) cout<<pri[i]<<" ";
        return 0;
    }
    

    6.求解同余方程:

    [求解:axequiv c(mod b)\ ax=by+c\ 即求解ax+by=c(正负无所谓\ 若方程有解,则:\ c=k imes gcd(a,b) kin N^*\ 扩展欧几里得定理求得的解为ax+by=exgcd(a,b)\ 若要求解ax+by=k imes exgcd(a,b)\在求解ax+by=exgcd(a,b)基础上,同乘k \x,y的通解: x+=b/gcd(a,b),y-=a/gcd(a,b) ]

    void exgcd(int a,int b,int &x,int &y) {
        if(b==0) {x=1;y=0;return a;}
        int g=exgcd(b,a%b,x,y);
        int t=x;
        x=y;
        y=t-a/b*x;
        return g;
    }
    

    7.中国剩余定理:

    (a_1,a_2 cdotscdots a_n)是两两互质的正整数,(M= prod_{i=1}^na_i,M_i=M/a_i)(t_i)是线性同余方程(M_it_i≡1(mod a_i))的一个解。对于任意的n个整数(b_1,b_2 cdots cdots b_n),则同余方程组:

    [egin{cases} xequiv b_1 (mod a_1)\ xequiv b_2 (mod a_2)\ xequiv b_3 (mod a_3)\ ……\ xequiv b_n (mod a_n)\ end{cases} ]

    有整数解,方程组的解为(x=b_1M_1t_1+b_2M_2t_2+ cdots cdots +b_nM_nt_n).并且在%M意义下有唯一解

    #include<bits/stdc++.h>
    #define ll long long
    
    using namespace std;
    
    int n;
    ll M,x,y,ans;
    ll a[15],b[15];
    
    ll exgcd(ll a,ll b,ll &x,ll &y) {
    	if(b==0) {x=1;y=0;return a;};
    	ll g=exgcd(b,a%b,x,y);
    	ll t=x;
    	x=y;
    	y=t-a/b*x;
    	return g;
    }
    
    void solve(int k) {
    	ll M_=M/a[k];
    	exgcd(M_,a[k],x,y);
    	ans=(ans+((x*M_)%M*b[k])%M+M)%M;
    }
    
    int main() {
    	scanf("%d",&n);
    	M=1;
    	for(int i=1;i<=n;i++) 
    		scanf("%lld%lld",&a[i],&b[i]),M*=a[i];
    	for(int i=1;i<=n;i++) 
    		solve(i);
    	printf("%lld",ans);
    	return 0;
    }
    

    8.树状数组:

    #include<bits/stdc++.h>
    #define ll long long
    
    using namespace std;
    
    ll n,m;
    ll c[1000000];
    
    ll lowbit(ll x) { return x&(-x);}
    
    void add(ll x,ll ad) {
    	while(x<=n) {
    		c[x]+=ad;
    		x+=lowbit(x);
    	}
    }
    
    ll sum(ll x) {
    	ll S=0;
    	while(x>0) {
    		S+=c[x];
    		x-=lowbit(x);
    	}
    	return S;
    }
    
    int main() {
    	 scanf("%lld%lld",&n,&m);
    	 for(int i=1,a;i<=n;i++) {
    	 	scanf("%d",&a);
    	 	add(i,a);
    	 }
    	 for(int i=1,opt,x,y;i<=m;i++) {
    		scanf("%d%d%d",&opt,&x,&y);
    		if(opt==1) 
    			add(x,y);
    		else 
    			printf("%lld
    ",sum(y)-sum(x-1));
    	 }
    	return 0;
    }
    

    9.线段树:

    #include<bits/stdc++.h>
    #define ll long long
    
    using namespace std;
    
    const int mxn=100010;
    
    int n,m;
    ll a[mxn];
    ll t[mxn<<2],tag[mxn<<2];
    
    void build(int k,int l,int r) {
    	if(l==r) {
    		t[k]=a[l];
    		return;
    	}
    	int mid=(l+r)>>1;
    	build(k<<1,l,mid);
    	build(k<<1|1,mid+1,r);
    	t[k]=t[k<<1]+t[k<<1|1];
    }
    
    void pushdown(int k,int l,int r) {
    	int mid=(l+r)>>1;
    	if(!tag[k]) return;
    	tag[k<<1]+=tag[k];
    	tag[k<<1|1]+=tag[k];
    	t[k<<1]+=(mid-l+1)*tag[k];
    	t[k<<1|1]+=(r-mid)*tag[k];
    	tag[k]=0;
    }
    
    void modify(int k,int l,int r,int x,int y,int q) {
    	if(x<=l&&r<=y) {
    		tag[k]+=q;
    		t[k]+=(r-l+1)*q;
    		return;
    	}
    	pushdown(k,l,r);
    	int mid=(l+r)>>1;
    	if(x<=mid) modify(k<<1,l,mid,x,y,q);
    	if(y>mid) modify(k<<1|1,mid+1,r,x,y,q);
    	t[k]=t[k<<1]+t[k<<1|1];
    }
    
    ll query(int k,int l,int r,int x,int y) {
    	if(x<=l&&r<=y) 
    		return t[k];
    	pushdown(k,l,r);
    	int mid=(l+r)>>1;
    	ll rtn=0;
    	if(x<=mid) rtn+=query(k<<1,l,mid,x,y);
    	if(y>mid) rtn+=query(k<<1|1,mid+1,r,x,y);
    	return rtn;
    }
    
    int main() {
    	scanf("%d%d",&n,&m);
    	for(int i=1;i<=n;i++) 
    		scanf("%lld",&a[i]);
    	build(1,1,n);
    	for(int i=1,opt,x,y,k;i<=m;i++) {
    		scanf("%d%d%d",&opt,&x,&y);
    		if(opt==1) {
    			scanf("%d",&k);
    			modify(1,1,n,x,y,k);
    		}
    		else 
    			printf("%lld
    ",query(1,1,n,x,y));
    	}
    }
    

    10.LCA:

    (树剖

    #include<bits/stdc++.h>
    
    using namespace std;
    
    const int mxn=500010;
    
    int n,m,S;
    struct node {
    	int to,nxt;
    }e[mxn<<1];
    int ecnt,head[mxn];
    void add(int from,int to) {
    	++ecnt;
    	e[ecnt].to=to;
    	e[ecnt].nxt=head[from];
    	head[from]=ecnt;
    }
    int fa[mxn],siz[mxn],dep[mxn],son[mxn];
    void dfs1(int u,int f) {
    	fa[u]=f;
    	siz[u]=1;
    	dep[u]=dep[f]+1; 
    	int maxn=-1;
    	for(int i=head[u],v;i;i=e[i].nxt) {
    		v=e[i].to;
    		if(v==f) continue;
    		dfs1(v,u);
    		siz[u]+=siz[v];
    		if(siz[v]>maxn) {
    			maxn=siz[v];
    			son[u]=v;
    		}
    	}
    }
    int top[mxn];
    void dfs2(int u,int f) {
    	if(son[f]==u) top[u]=top[f];
    	else top[u]=u;
    	if(son[u]) dfs2(son[u],u);
    	for(int i=head[u],v;i;i=e[i].nxt) {
    		v=e[i].to;
    		if(v==f||v==son[u]) continue;
    		dfs2(v,u);
    	}
    }
    
    int getlca(int x,int y) {
    	while(top[x]!=top[y]) {
    		if(dep[top[x]]>dep[top[y]]) 
    			x=fa[top[x]];
    		else 
    			y=fa[top[y]];
    	}
    	if(dep[x]>dep[y]) return y;
    	else return x;
    }
    
    int main() {
    	scanf("%d%d%d",&n,&m,&S);
    	for(int i=1,x,y;i<n;i++) {
    		scanf("%d%d",&x,&y);
    		add(x,y);
    		add(y,x);
    	}
    	dfs1(S,0);
    	dfs2(S,0);
    	for(int i=1,a,b,lca;i<=m;i++) {
    		scanf("%d%d",&a,&b);
    		lca=getlca(a,b);
    		printf("%d
    ",lca);
    	}
    	return 0;
    }
    

    倍增:

    #include<bits/stdc++.h>
    
    using namespace std;
    
    const int mxn=500010;
    
    int n,m,S;
    struct node {
    	int to,nxt;
    }e[mxn<<1];
    int ecnt,head[mxn];
    void add(int from,int to) {
    	++ecnt;
    	e[ecnt].to=to;
    	e[ecnt].nxt=head[from];
    	head[from]=ecnt;
    }
    int fa[mxn][20],dep[mxn];
    void dfs(int u,int f) {
    	fa[u][0]=f;
    	for(int i=1;i<=19;i++)
    		fa[u][i]=fa[fa[u][i-1]][i-1];
    	dep[u]=dep[f]+1; 
    	for(int i=head[u],v;i;i=e[i].nxt) {
    		v=e[i].to;
    		if(v==f) continue;
    		dfs(v,u);
    	}
    }
    
    int getlca(int x,int y) {
    	if(dep[x]>dep[y]) swap(x,y);
    	for(int i=19;i>=0;i--) 
    		if(dep[fa[y][i]]>=dep[x]) 
    			y=fa[y][i];
    	if(x==y) return x;
    	for(int i=19;i>=0;i--) {
    		if(fa[x][i]!=fa[y][i]) {
    			x=fa[x][i];
    			y=fa[y][i];
    		}
    	}
    	return fa[x][0];
    }
    
    int main() {
    	scanf("%d%d%d",&n,&m,&S);
    	for(int i=1,x,y;i<n;i++) {
    		scanf("%d%d",&x,&y);
    		add(x,y);
    		add(y,x);
    	}
    	dfs(S,0);
    	for(int i=1,x,y,lca;i<=m;i++) {
    		scanf("%d%d",&x,&y);
    		lca=getlca(x,y);
    		printf("%d
    ",lca);
    	}
    	return 0;
    }
    

    12.堆:

    #include<bits/stdc++.h>
    #define pa pair<int,int>
    #define mk make_pair
    
    using namespace std;
    
    inline int read() {
    	int ans=0;
    	char last=' ',ch=getchar();
    	while(ch>'9'||ch<'0') last=ch,ch=getchar();
    	while(ch>='0'&&ch<='9') ans=(ans<<1)+(ans<<3)+ch-'0',ch=getchar();
    	if(last=='-') ans=-ans;
    	return ans; 
    }
    
    int n,siz;
    int heap[1000080];
    
    void insert(int x) {
    	heap[++siz]=x;
    	int nxt,now=siz;
    	while(now>1) {
    		nxt=now>>1;
    		if(heap[nxt]<=heap[now]) break;
    		swap(heap[now],heap[nxt]);
    		now=nxt; 
    	}
    }
    
    void Delete() {
    	heap[1]=heap[siz--];
    	int now=1,nxt;
    	while((now<<1)<=siz) {
    		nxt=now<<1;
    		if(nxt<siz&&heap[nxt+1]<heap[nxt]) nxt++;
    		if(heap[now]<=heap[nxt]) break;
    		swap(heap[now],heap[nxt]);
    		now=nxt;
    	}
    }
    
    int main() {
    	n=read();
    	for(int i=1,opt,x;i<=n;i++) {
    		opt=read();
    		if(opt==1) {
    			x=read();
    			insert(x);
    		}
    		if(opt==2)
    			printf("%d
    ",heap[1]);
    		if(opt==3)
    			Delete(); 
    	}
    	return 0;
    }
    
    

    13.逆元:

    定义:

    (axequiv 1(mod b)),且a与b互质,那么我们就能定义: x为a的逆元,记为(a^{-1}),所以我们也可以称 x 为 a 在 (mod b) 意义下的倒数,

    1.扩展欧几里得算法:

    由逆元定义可知,求a在mod b意义下的逆元,就是求ax+by=1的解,因此我们可以使用扩欧算法:

    int exgcd(int a,int b,int &x,int &y) {
        if(b==0){x=1;y=0;return a;}
        int g=exgcd(b,a%b,x,y);
        int t=x;
        x=y;
        y=t-a/b*x;
    }
    
    

    2.利用费马小定理或者欧拉定理

    费马小定理:

    如果 a,p 互质,那么 (a^{p-1} ≡ 1 (mod p))

    由此可以推出,(a^{-1}=a^{p-2})

    那么我们就可以用快速幂来完成求逆元的任务;

    欧拉定理:

    如果a,p互质,那么(a^{phi(p)} ≡ 1 ;(mod; p)),当 p 为质数时,(phi(p)=p-1)

    欧拉函数怎么求?

    (只顺手写个快速幂行吧?)

    ll quick_pow(int x,int k) {
        ll ans=1;
        while(k){
            if(k&1) ans=(ans*x)%mod;
            x=(x*x)%mod;
        }
        return ans;
    }
    
    

    3.线性递推(用于求解一段数的逆元

    [令p=ki+r;k=leftlfloordfrac{p}{i} ight floor,r=p\%i (i<p,k<p,r<i)\ 则有:ki+requiv 0(mod p)①\ ①式左右同乘i^{-1} imes r^{-1}得:\ kr^{-1}+i^{-1}equiv 0(mod p)\ 移项得:i^{-1} equiv -k*r^{-1} (mod p)  \ 带入 k=leftlfloordfrac{p}{i} ight floor,r=p\%i\   i^{-1}equiv -leftlfloordfrac{p}{i} ight floor*(pmod i)^{-1}(mod p)\ 由于(pmod i)<i\ 因此在求出i^{-1}之前,我们已经求出(pmod i)^{-1}\ 用inv数组记录逆元 则:inv[i]=-leftlfloordfrac{p}{i} ight floor*inv[pmod i] mod p\ 为了保证逆元>0,所以要在右边+p,即:inv[i]=-leftlfloordfrac{p}{i} ight floor*inv[pmod i]+p mod p\ inv[1]=1;inv[0]=tanfrac{π}{2}设为0 ]

    #include<bits/stdc++.h>
    #define ll long long
    
    using namespace std;
    
    int n,p;
    ll inv[3000010];
    
    int main() {
    	scanf("%d%d",&n,&p);
    	inv[1]=1;
    	puts("1");
    	for(int i=2;i<=n;i++) {
    		inv[i]=((-(p/i)*inv[p%i]+p)%p+p)%p;
    		printf("%lld
    ",inv[i]);
    	}
    	return 0;
    }
    
    

    14.矩阵加速:(模板

    [a[1]=a[2]=a[3]=1;\ a[x]=a[x-1]+a[x-3] (a>3) ]

    转移矩阵:

    [egin{vmatrix}a_3\a_{2}\a_{1}end{vmatrix} imes egin{vmatrix}1&0&1\1&0&0\0&1&0end{vmatrix}^{n-3}=egin{vmatrix}a_{n}\a_{n-1}\a_{n-2}end{vmatrix} ]

    15.高精度:

    #include<bits/stdc++.h>
    
    using namespace std;
    
    char A[10090],B[10090];
    int a[10090],b[10090],c[10090]; 
    
    void sum() {
    	scanf("%s",A);
    	int lena=strlen(A);
    	for(int i=0;i<lena;i++)
    		a[lena-i]=A[i]-'0';
    	scanf("%s",B);
    	int lenb=strlen(B);
    	for(int i=0;i<lenb;i++)
    		b[lenb-i]=B[i]-'0';
    	int len=max(lena,lenb);
    	for(int i=1;i<=len;i++) {
    		c[i]=a[i]+b[i];
    	}
    	for(int i=1;i<=len;i++) {
    		c[i+1]+=(c[i]/10);
    		c[i]%=10;
    	}
    	if(c[len+1]!=0) len++;
    	for(int i=len;i>=1;i--)
    		printf("%d",c[i]); 
    }
    
    void jian(){
    		int bj=1;
    	scanf("%s",A);
    	scanf("%s",B);
    	int lena=strlen(A);
    	int lenb=strlen(B);
    	if(lena<lenb) {
    		bj=-1;
    		swap(A,B);
    		swap(lena,lenb);
    	}
    	if(lena==lenb&&strcmp(A,B)<0) {
    		bj=-1;
    		swap(A,B);
    		swap(lena,lenb);
    	}
    	
    	for(int i=0;i<lena;i++)
    		a[lena-i]=A[i]-'0';
    	
    	
    	for(int i=0;i<lenb;i++)
    		b[lenb-i]=B[i]-'0';
    	int len=max(lena,lenb);
    	for(int i=1;i<=len;i++)
    		c[i]=a[i]-b[i];
    	for(int i=1;i<=len;i++) {
    		if(c[i]<0) {
    			c[i]+=10;
    			c[i+1]--;
    		}
    	} 
    	if(bj==-1) printf("-");
    	while(c[len]==0&&len>1) len--;
    	for(int i=len;i>=1;i--) 
    		printf("%d",c[i]);
    }
    
    void Mul() {
    	scanf("%s",A);
    	int lena=strlen(A);
    	for(int i=0;i<lena;i++)
    		a[lena-i]=A[i]-'0';
    	scanf("%s",B);
    	int lenb=strlen(B);
    	for(int i=0;i<lenb;i++)
    		b[lenb-i]=B[i]-'0';
    	for(int i=1;i<=lena;i++) 
    		for(int j=1;j<=lenb;j++) 
    			c[i+j-1]+=a[i]*b[j];
    	for(int i=1;i<=lena+lenb-1;i++) {
    		c[i+1]+=(c[i]/10);
    		c[i]%=10;
    	}
    	int len=lena+lenb-1;
    	while(c[len+1]>0) {
    		c[len+2]+=(c[len+1]/10);
    		c[len+1]%=10;
    		len++;
    	}
    	for(int i=len;i>=1;i--)
    		printf("%d",c[i]);
    }
    
    int main() {
    	scanf("%s",A);
    	int lena=strlen(A);
    	for(int i=0;i<lena;i++)
    		a[lena-i]=A[i]-'0';
    	int B;
    	scanf("%d",&B);
    	for(int i=lena;i>=1;i--) {
    		c[i]=a[i]/B;
    		a[i-1]+=(a[i]%B)*10;
    	}
    	while(c[lena]==0&&lena>0) lena--;
    	for(int i=lena;i>=1;i--)
    		printf("%d",c[i]);
    	return 0;
    }
    
    

    16.ST表:

    #include<bits/stdc++.h>
     
    using namespace std;
    
    typedef long long ll;
    typedef unsigned long long ull;
    const int inf=2147483647;
    inline ll read()
    {
        char ch=getchar();
        ll x=0; 
        bool f=0;
        while(ch<'0'||ch>'9')
        {
            if(ch=='-') f=1;
            ch=getchar();
        }
        while(ch>='0'&&ch<='9')
        {
            x=(x<<3)+(x<<1)+(ch^48);
            ch=getchar();
        }
        return f?-x:x;
    }
    int n,m,a[1000009],st[1000009][23];
    int lg[100009];
    int qry(int l,int r)
    {
        int qwq=log((double)(r-l+1))/log(2.0);
        return max(st[l][qwq],st[r-(1<<qwq)+1][qwq]);
    }
    int main()
    {
        n=read();m=read();
        for(int i=1;i<=n;i++)
        {
            a[i]=read();
            st[i][0]=a[i];
        }
        for(int i=1;(1<<i)<=n;i++)
        {
            for(int j=1;j<=n;j++)
            {
                st[j][i]=max(st[j][i-1],st[j+(1<<(i-1))][i-1]);
            }
        }
        while(m--)
        {
            int l=read(),r=read();
            printf("%d
    ",qry(l,r));
        }
    }
    
    

    17.高斯消元:

    #include<iostream>
    #include<algorithm>
    #include<cstdio>
    #include<cstring>
    #include<cmath>
    #include<cstdlib>
    using namespace std;
    typedef long long ll;
    typedef long double ld;
    typedef pair<int,int> pr;
    const double pi=acos(-1);
    #define rep(i,a,n) for(int i=a;i<=n;i++)
    #define per(i,n,a) for(int i=n;i>=a;i--)
    #define Rep(i,u) for(int i=head[u];i;i=Next[i])
    #define clr(a) memset(a,0,sizeof a)
    #define pb push_back
    #define mp make_pair
    #define fi first
    #define sc second
    ld eps=1e-9;
    ll pp=1000000007;
    ll mo(ll a,ll pp){if(a>=0 && a<pp)return a;a%=pp;if(a<0)a+=pp;return a;}
    ll powmod(ll a,ll b,ll pp){ll ans=1;for(;b;b>>=1,a=mo(a*a,pp))if(b&1)ans=mo(ans*a,pp);return ans;}
    ll read(){
        ll ans=0;
        char last=' ',ch=getchar();
        while(ch<'0' || ch>'9')last=ch,ch=getchar();
        while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
        if(last=='-')ans=-ans;
        return ans;
    }
    //head(lh的代码头)
    int n,m;
    double a[100][100];
    
    bool check(int k){
        if(fabs(a[k][n+1])<eps)return 1;// 如果小于0,返回1 
        for(int i=1;i<=n;i++) 
            if(fabs(a[k][i])>eps)return 1;//第k行的每个数都大于0 
        return 0;
    }
    int main(){
        n=read();m=read();//m*n的矩阵,
        // a_i,1 a_i,2 ... a_i,n a_i,n+1
        for(int i=1;i<=m;i++)
            for(int j=1;j<=n+1;j++)a[i][j]=read();//输入矩阵元素(因为除了这个m*n的矩阵,还要有一行答案qwq) (看洛谷题吧qwq) 
        for(int j=1;j<=m;j++){
                for(int k=1;k<=n+1;k++)cout<<a[j][k]<<" ";
                puts("");
            }//先把矩阵输出辽一遍 
        int flag=0;
        for(int i=1;i<=n;i++){
            int t=i;
            while(a[t][i]==0 && t<=n)t+=1;
            if(t==n+1){
                flag=1;
                continue;
            }//if判断是否有一行全为0,如果全为0 那么我们就少了至少1个方程,那么这个方程显然无唯一解 
            for(int j=1;j<=n+1;j++)swap(a[i][j],a[t][j]);//交换第i行和第t行的值,目的在于交换第i行和第t行后可以使a[1][1]!=0 
            double kk=a[i][i];//找到对角线qwq 
            for(int j=1;j<=n+1;j++)a[i][j]/=kk;//把这一行的每一项都除以对角线,使得对角线为1 
            for(int j=1;j<=m;j++) //这里真的要详细地讲一讲咯 
                if(i!=j){//首先i!=j这样就不再消对角线上的数了 
                    double kk=a[j][i];//定义kk为第j行第i列的数 
                    for(int k=1;k<=n+1;k++)//把每一项消成0qwq(先把第一列除了对角线全消为0然后第二第三……) 
                    // 关于处理对角线这里以i=1,j=3做例子:当k=3时,a[3][3]-=a[3][1]*a[1][3]而这个时候a[3][1]已经为0,故对对角线无影响 
                        a[j][k]-=kk*a[i][k];
                }
            puts("------------");//画一个杠杠来分割每一次消元结果 
            for(int j=1;j<=m;j++){
                for(int k=1;k<=n+1;k++)cout<<a[j][k]<<" ";//输出每次消元结果 
                puts("");//输出空格 
            }
        }
        if(flag){//判断无解和多解的情况(上面已经提到了) 已经懵bi求救qwq 
            for(int i=1;i<=m;i++) 
                if(!check(i)){//利用check判断是无解还是多解  
                    printf("No solution
    ");
                    return 0;
                }
                //每个答案行如果有一个等于0的数就多解??
            printf("So many solutions
    ");
        }
    }
    -------------------------
    #include<iostream>
    #include<algorithm>
    #include<cstdio>
    #include<cstring>
    #include<cmath>
    #include<cstdlib>
    using namespace std;
    long long read(){
        long long ans=0;
        char last=' ',ch=getchar();
        while(ch<'0' || ch>'9')last=ch,ch=getchar();
        while(ch>='0' && ch<='9')ans=ans*10+ch-'0',ch=getchar();
        if(last=='-')ans=-ans;
        return ans;
    }
    int n,m;
    double a[100][100];
    
    int main(){
        n=read();
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n+1;j++)a[i][j]=read(); 
        int flag=0;
        for(int i=1;i<=n;i++){
            int t=i;
            while(a[t][i]==0 && t<=n)t+=1;
            if(t==n+1){
                flag=1;
                continue;
            }
            for(int j=1;j<=n+1;j++)swap(a[i][j],a[t][j]);
            double kk=a[i][i];
            for(int j=1;j<=n+1;j++)a[i][j]/=kk;
            for(int j=1;j<=n;j++) 
                if(i!=j){
                    double kk=a[j][i];
                    for(int k=1;k<=n+1;k++)
                        a[j][k]-=kk*a[i][k];
                }  
            }
        if(flag)printf("No Solution
    ");
        else {for(int i=1;i<=n;i++)
             printf("%.2lf
    ",a[i][n+1]);}
             return 0;
    }
    //和上面代码差不多的,只不过这个输出的是第n+1行,也就是每一个未知数的解(因为都消成1了qwq)
    
    

    18.矩阵求逆:

    #include<cstdio>
    #include<iostream>
    using namespace std;
    typedef long long LL;
    const int N=405;
    int mod;
    int n,m;
    LL f[N][N<<1];//与下文相照应,这里N<<1指N/2,为了构造单位矩阵而乘的2 
    LL r,ret;
    LL ksm(LL u,LL v){ 
    	ret=1;
    	while(v){
    		if(v&1)ret=ret*u%mod;
    		u=u*u%mod;v>>=1;
    	}
    	return ret;
    }
    int main(){
    	scanf("%d%d",&n,&mod);
        m=n*2; //乘2是为了后面建立一个单位矩阵 
    	for(int i=1;i<=n;++i){
    		for(int j=1;j<=n;j++)
                scanf("%lld",&f[i][j]);//输入n*n的矩阵 
    		f[i][n+i]=1; //在 f后面又搞了一个单位矩阵qwq 
    	}
    	for(int i=1;i<=n;++i){ //高斯消元的板子
    		for(int j=i;j<=n;j++)
    			if(f[j][i]){
    				for(int k=1;k<=m;k++)
    					swap(f[i][k],f[j][k]); 
    				break;
    			}
    		if(!f[i][i]){
           		puts("No Solution");
            	return 0;
        	} //判断是否有解(对角线为0) 
    		r=ksm(f[i][i],mod-2); 
    		for(int j=i;j<=m;++j) 
    			f[i][j]=f[i][j]*r%mod;
    		for(int j=1;j<=n;++j) 
    			if(j!=i){
    				r=f[j][i];
    				for(int k=i;k<=m;++k)
    					f[j][k]=(f[j][k]-r*f[i][k]%mod+mod)%mod;
    			}
    }
    	for(int i=1;i<=n;++i,puts(""))
    		for(int j=n+1;j<=m;++j)
       			printf("%lld ",f[i][j]);
    	return 0;
    }
    
    
  • 相关阅读:
    JSTL 标签库<转>
    EL表达式 <转>
    前端知识点记录
    spring boot 项目连接数据库查询数据过程
    vue -电子时钟
    XML读取
    Druid 连接池
    java JDBC自我总结
    各种数据库的链接方式总结
    Java MD5获取
  • 原文地址:https://www.cnblogs.com/zhuier-xquan/p/11864146.html
Copyright © 2011-2022 走看看