23暑假友谊赛

23暑假友谊赛

马猴烧酒

思路:枚举对行的所有可能操作,判断列需要的操作次数是否满足条件;

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e4+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;

string s[25];
void solve(){
    int n,m,a,b;cin>>n>>m>>a>>b;
    for(int i=0;i<n;++i){
        cin>>s[i];
    }
    for(int i=0;i<(1<<n);++i){
        int cnt=__builtin_popcount(i);
        if(cnt>a)continue;
        set<int>se;
        for(int j=0;j<n;++j){
            if(!(i&(1<<j))){
                for(int k=0;k<m;++k){
                    if(s[j][k]=='*')se.insert(k);
                }
            }
        }
        if(se.size()<=b){
            cout<<"yes\n";return;
        }
    }
    cout<<"no\n";
    return ;
}

signed main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int T=1;
    //init();
    cin>>T;
    while(T--){
        solve();
    }
    return 0;
}
View Code

 

阶乘

思路:要求n!是p的倍数,说明n!的因子包含p的全部因子。

统计出p的所有因子,及其个数,那么p=a1k1*a1k2*...*amkm

由于ai都是互质的,需要!n中的每种质因子是相互不影响的;

单独求出包含每种质因子全部个数的最小n,对所有n取最大即可;

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e6+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;
int prime[N],cnt[N],idx,p;
bool check(int x){
    for(int i=1;i<=idx;++i){
        int s=0,n=x;
        while(n){
            s+=n/prime[i];
            n/=prime[i];
        }
        if(s<cnt[i])return false;
    }
    return true;
}
void solve(){
    cin>>p;
    idx=0;
    for(int i=2;i<=p/i;++i){
        if(p%i==0){
            prime[++idx]=i;
            while(p%i==0){
                cnt[idx]++;
                p/=i;
            }
        }
    }
    if(p>1)prime[++idx]=p,cnt[idx]++;
    int l=1,r=1e9,ans;
    while(l<=r){
        int mid=l+r>>1;
        if(check(mid))r=mid-1,ans=mid;
        else l=mid+1;
    }
    cout<<ans<<'\n';
    memset(prime,0,sizeof prime);
    memset(cnt,0,sizeof cnt);
}
signed main(){

    //ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int t=1;
    //init();
    cin>>t;
    while(t--){
        solve();
    }
    return 0;
}
View Code

 

完全图

思路:求所有边的贡献,对于一条边,过这条边的链的数目为:以这条边两端点为根节点的子节点数(包括自己)的乘积。

将所有边的次数排序,次数越大的权值越小

#include<bits/stdc++.h>
using namespace std;
//#define int long long
#define int __int128
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e5+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;
int read()
{
    int res=0;
    char scan[1005];
    scanf("%s",scan);
    for(int i=0;i<strlen(scan);i++)
        res*=10,res+=scan[i]-'0';
    return res;
}

int n,m,mm;
bool check(int k){
    int b=n-k+1;
    int y=b*(b-1)/2;
    int le=mm-y;
    return le<=m;
}
void solve(){
    n=read(),m=read();
    mm=n*(n-1)/2;
    int l=1,r=n,ans;
    while(l<=r){
        int mid=l+r>>1;
        if(check(mid))ans=mid,l=mid+1;
        else r=mid-1;
    }
    cout<<(long long)ans<<'\n';
    return ;
}

signed main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int T=1;
    //init();
    T=read();
    while(T--){
        solve();
    }
    return 0;
}
View Code

 

A+B问题

思路:a和b的范围为 l~r,l= -2147483648 ,r=2147483647,且a+b=c;

定a1=l,b1=c-a1

定a2=r,b2=c-a2

答案为b1-b2+1=a2-a1+1

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e4+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;

//string s[25];
void solve(){
    /*int n,m,a,b;cin>>n>>m>>a>>b;
    for(int i=0;i<n;++i){
        cin>>s[i];
    }*/
    int n;cin>>n;
    int a1=-2147483648,a2=2147483647;
    int b1=n-a1,b2=n-a2;
    cout<<b1-b2+1;
}
//-2147483648 ~ 2147483647
signed main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int T=1;
    //init();
    //cin>>T;
    while(T--){
        solve();
    }
    return 0;
}
View Code

 

 树上求和

思路:求所有边的贡献,对于一条边,过这条边的链的数目为:以这条边两端点为根节点的子节点数(包括自己)的乘积。

将所有边的次数排序,次数越大的权值越小

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e5+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;
int h[N],ne[2*N],e[2*N],idx;
int cnt[N];
void add(int a,int b){
    e[idx]=b,ne[idx]=h[a],h[a]=idx++;
}
void dfs(int u,int fa){
    cnt[u]=1;
    for(int i=h[u];i!=-1;i=ne[i]){
        int j=e[i];
        if(j==fa)continue;
        dfs(j,u);
        cnt[u]+=cnt[j];
    }
}
void solve(){
    int n;cin>>n;
    memset(h,-1,sizeof h);
    for(int i=1,u,v;i<n;++i){
        cin>>u>>v;
        add(u,v);
        add(v,u);
    }
    dfs(1,0);
    vector<int>ve;
    for(int i=2;i<=n;++i){
        ve.push_back(cnt[i]*(n-cnt[i]));
    }
    sort(ve.begin(),ve.end(),greater<int>());
    int ans=0;
    for(int i=1;i<n;++i){
        ans+=i*ve[i-1];
    }
    cout<<ans;
}
signed main(){

    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int t=1;
    //init();
    //cin>>t;
    while(t--){
        solve();
    }
    return 0;
}
View Code

 

奇怪的背包问题增加了

思路:230=2*229,229=2*228,...

可以搜索找到凑成230的所有数,找不到则impossible

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e5+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;

int have[35];
int cost[35];
int a[N];
bool dfs(int u,int c){
    if(u<0)return false;
    cost[u]=min(c,have[u]);
    if(have[u]>=c)return true;
    //if(u==0)return false;
    return dfs(u-1,(c-have[u])*2);
}
void solve(){
    int m;cin>>m;
    memset(have,0,sizeof have);
    memset(cost,0,sizeof cost);
    for(int i=0;i<m;++i){
        cin>>a[i];
        have[a[i]]++;
    }
    bool ok=dfs(30,1);
    if(!ok){
        cout<<"impossible\n";
    }else{
        for(int i=0;i<m;++i){
            if(cost[a[i]]){
                cout<<1;cost[a[i]]--;
            }else cout<<0;
        }cout<<'\n';
    }
    return ;
}

signed main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int T=1;
    //init();
    cin>>T;
    while(T--){
        solve();
    }
    return 0;
}
View Code

 

寻找子串

思路:暴力枚举每种子串

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e4+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;

//string s[25];
void solve(){
    /*int n,m,a,b;cin>>n>>m>>a>>b;
    for(int i=0;i<n;++i){
        cin>>s[i];
    }*/
    string s;cin>>s;
    string ans="-1";
    for(int i=1;i<=s.size();++i){
        for(int j=0;j+i-1<s.size();++j){
            string a=s.substr(j,i);
            if(ans=="-1"||a>ans)ans=a;
        }
    }
    cout<<ans;
}
//-2147483648 ~ 2147483647
signed main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int T=1;
    //init();
    //cin>>T;
    while(T--){
        solve();
    }
    return 0;
}
View Code

 

最大的差

思路:排个序,首位就是相差最大的

#include<bits/stdc++.h>
using namespace std;
#define int long long
typedef pair<int,int>PII;

typedef pair<string,int>PSI;
typedef pair<string,string>PSS;
const int N=1e4+5,INF=0x3f3f3f3f,Mod=1e9+7;
const double eps=1e-6;

//string s[25];
void solve(){
    /*int n,m,a,b;cin>>n>>m>>a>>b;
    for(int i=0;i<n;++i){
        cin>>s[i];
    }*/
    int n;cin>>n;
    vector<int>a(n);
    for(int i=0;i<n;++i)cin>>a[i];
    sort(a.begin(),a.end());
    cout<<abs(a[n-1]-a[0]);
}
signed main(){
    ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
    int T=1;
    //init();
    //cin>>T;
    while(T--){
        solve();
    }
    return 0;
}
View Code

 

posted @ 2023-07-20 10:14  bible_w  阅读(4)  评论(0编辑  收藏  举报