一共个人认为三道题比较难做,也没有一次过。
T1:
?一道大字符串模拟,要处理的细节真是很多很多,第一次少分析了情况,第二次是多测没清空。。虽然我认为我的代码不需要清空,但事实证明需要。然后个人的代码还比较冗长吧,但是很好看懂,思路也很清晰。
#include<bits/stdc++.h>
#define re register
using namespace std;
inline int read(){
int x=0,f=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch == '-') f=-1 ; ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48) ; ch=getchar();}
return x*f;
}
inline void print(int x){
if(x/10) print(x/10);
putchar(x%10+'0');
}
const int M = 1e5+10;
int t[M];
int T;
char s[M];
int ff[M];
int head=1,tail=0;
inline bool check(char ch){
for(re int i(head) ; i<=tail ; ++i) if(s[i]==ch) return 0;
return 1;
}
signed main(){
//freopen("a.in","r",stdin);
//freopen("a.out","w",stdout);
T=read();
while(T--){
memset(t,0,sizeof(t));
memset(s,0,sizeof(s));
memset(ff,0,sizeof(ff));
int ans=0;
int shijiancnt=0;
int fcnt=0;
int shijian=0;
int jilu=0;
int n=read();
string ss;
getline(cin,ss);
int sum = 0;
int flag = 0;
for(re int i(0) ; i<ss.length() ; ++i){
if(ss[i]>='0'&&ss[i]<='9') sum=sum*10+ss[i]-'0';
if(ss[i]=='n') flag = 1;
}
if(flag == 0) shijian = 0;
else shijian = sum;
head=1,tail=0;
int jin=0;
int xuyao=0;
for(re int xxx(1) ; xxx<=n ; ++xxx){
string a;
getline(cin,a);
if(jilu == 1) continue;
int len = a.length();
if(a[0] == 'E'){
ans = max(ans,shijiancnt);
if(ff[tail] == 1) shijiancnt--,ff[tail]=0;
tail--;
if(tail<0) jilu = 1;
fcnt--;
if(xuyao != 0) xuyao--;
//cout << ans << endl;
continue;
}
if(a[0] == 'F'){
fcnt++;
int pos1=0,pos2=0;
char bianliang,ed;
int tou=-1,wei=-1;
int flag1=0,flag2=0;
int sum=0;
for(re int i(0) ; i<len ; ++i){
if(a[i]>='a'&&a[i]<='z'&&flag1==0){
bianliang=a[i],flag1=1;
continue;
}
if(a[i]>='a'&&a[i]<='z'&&flag1==1){
ed=a[i],pos1=i;
continue;
}
if(a[i]>='0'&&a[i]<='9'&&flag2==0){
if(a[i+1]>='0'&&a[i+1]<='9') sum=sum*10+a[i]-'0';
else{
tou=sum*10+a[i]-'0',flag2=1,pos2=i,sum=0;
continue;
}
}
if(a[i]>='0'&&a[i]<='9'&&flag2==1){
if(a[i+1]>='0'&&a[i+1]<='9') sum=sum*10+a[i]-'0';
else{
wei=sum*10+a[i]-'0';
continue;
}
}
}
if(check(bianliang)==0) jilu = 1;
s[++tail] = bianliang;
if(tou==-1 && wei==-1) continue;
if((pos1<pos2&&pos1!=0) || (tou>wei&&wei!=-1) || xuyao!=0) xuyao++;
if(pos1>pos2 && xuyao==0) shijiancnt++,ff[tail] = 1;
//cout << shijiancnt << endl;
//cout << tou << " " << wei << " " << bianliang << " " << ed << " " << pos1 << " " << pos2 << " " << xuyao << " " << shijiancnt << endl;
}
}
if(jilu == 1 || fcnt!=0) cout << "ERR" << endl;
else{
if(ans != shijian) cout << "No" << endl;
else cout << "Yes" << endl;
}
}
return 0;
}
T2:
当然,这道题现在也不会,就是打了暴力的27分,K=0的情况(虽然我感觉我的应该是对的,但全TLE了)。嗯。。正解应该挺复杂的,代码能力不够。
#include<bits/stdc++.h>
#define re register
using namespace std;
inline int read(){
int x=0,f=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch == '-') f=-1 ; ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48) ; ch=getchar();}
return x*f;
}
inline void print(int x){
if(x/10) print(x/10);
putchar(x%10+'0');
}
const int M = 2e5+10;
const int inf = INT_MAX;
typedef pair<int,int> pii;
int T;
int n,m,k,p;
int dis[M],head[M],head2[M],f[M],bo[M],vis[M];
int cnt,cnt2,ans;
struct edge{
int to,nxt,w;
}e[M];
inline void add(int u,int v,int w){
e[++cnt].to = v;
e[cnt].w = w;
e[cnt].nxt = head[u];
head[u] = cnt;
}
struct edge2{
int to,nxt;
}e2[M];
inline void add2(int u,int v){
e2[++cnt2].to = v;
e2[cnt2].nxt = head2[u];
head2[u]=cnt2;
}
inline void init(){
memset(dis,0,sizeof(dis));
memset(head,0,sizeof(head));
memset(head2,0,sizeof(head2));
memset(f,0,sizeof(f));
memset(bo,0,sizeof(bo));
memset(vis,0,sizeof(vis));
cnt = cnt2 = ans = 0;
}
inline void dfs1(int u){
bo[u] = 1;
for(re int i(head2[u]) ; i ; i=e2[i].nxt){
int v = e2[i].to;
if(!bo[v]) bo[v]=1,dfs1(v);
}
}
inline void dij(int s){
priority_queue<pii,vector<pii>,greater<pii> >q;
for(re int i(1) ; i<=n ; ++i) dis[i] = inf;
dis[s] = 0;
q.push(make_pair(0,s));
while(!q.empty()){
int u = q.top().second;
q.pop();
if(vis[u]) continue;
vis[u] = 1;
for(re int i(head[u]) ; i ; i=e[i].nxt){
int v = e[i].to,w = e[i].w;
if(dis[v] > dis[u]+w){
dis[v] = dis[u]+w;
q.push(make_pair(dis[v],v));
}
}
}
}
inline void dfs2(int u,int sum){
if(!bo[u]) return;
if(u == n) {ans++;ans%=p;return;}
for(re int i(head[u]) ; i ; i=e[i].nxt){
int v = e[i].to,w = e[i].w;
if(sum + w - dis[v] > k) continue;
dfs2(v,sum+w);
}
}
signed main(){
T=read();
while(T--){
init();
n=read(),m=read(),k=read(),p=read();
for(re int i(1) ; i<=m ; ++i){
int u=read(),v=read(),w=read();
add(u,v,w);
add2(v,u);
}
dfs1(n);
dij(1);
dfs2(1,0);
printf("%d\n",ans);
}
return 0;
}
?T3:
一道状压的题,感觉上不是很难,写起来代码也不长,但是要处理的细节还是要处理好。
#include<bits/stdc++.h>
#define re register
using namespace std;
inline int read(){
int x=0,f=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch == '-') f=-1 ; ch=getchar();}
while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+(ch^48) ; ch=getchar();}
return x*f;
}
inline void print(int x){
if(x/10) print(x/10);
putchar(x%10+'0');
}
const int M = (1<<13);
const int N = 20;
const int inf = INT_MAX;
int n,m;
int f[M],a[N][N],dis[M];
int ans = inf;
inline void dfs(int zt){
for(re int i(1) ; i<=n ; ++i){
if(!((1<<(i-1))&zt)) continue;
for(re int j(1) ; j<=n ; ++j){
if(a[i][j]==0x3f3f3f3f || i==j) continue;
if(f[zt|(1<<(j-1))] > f[zt] + a[i][j]*dis[i]){
int res = dis[j];
dis[j] = dis[i] + 1;
f[zt|(1<<(j-1))] = f[zt] + a[i][j]*dis[i];
dfs(zt|(1<<(j-1)));
dis[j] = res;
}
}
}
}
signed main(){
n=read(),m=read();
memset(a,0x3f,sizeof(a));
for(re int i(1) ; i<=m ; ++i){
int u=read(),v=read(),w=read();
a[u][v] = min(a[u][v],w);
a[v][u] = min(a[v][u],w);
}
for(re int i(1) ; i<=n ; ++i){
memset(f,0x3f,sizeof(f));
memset(dis,0x3f3f3f3f,sizeof(dis));
dis[i] = 1;
f[1<<(i-1)] = 0;
dfs(1<<(i-1));
ans = min(ans,f[(1<<n)-1]);
}
printf("%d",ans);
return 0;
}
?
|