NEUQ-ACM预备队训练-week3(线性表)

前言及题解思路

第一次做数据结构方面的题目,感觉题目比较复杂,需要注意很多细节,需要对题目 进行充分的分析,并有着清晰的思路

  • 第一题可以说是这四个题里面最简单的了,只需要完成存储和查找的功能,其中清空格子的代码可以省略,因为题目中有一句“保证查询的柜子有存过东西”(乐),但需要注意的一点是开二维数组的话会因为数组过大而爆掉,所以我采用了map进行存储
  • 第二题的关键是理解题目的含义,判断出具体的配对条件,对可能出现的排列顺序进行分析,我采用了比较基础的方法,对出现的右括号往前查找是否满足配对的条件,满足的话用数组对这个位置进行标记(是否配对),最后再对未配对的括号补全输出即可
  • 第三题我采用了单向链表+栈的方法,以题目中出现的各种符号为链表节点,对每个" . "节点,我获取了上一个节点和该“ . ”节点之间的数据,把其转化为数值存储到栈中,存储完数据之后,接下来开始处理算术运算符,当遇到±*/这些符号的节点时,按照入栈的顺序取出新入栈的两个数据进行算数运算,直到处理到最后只剩最后一个数据
  • 第四题和学习通资料markdown教程里面的例题的思路是一样的,相对二三题比较简单,只需要实现一个双向链表的过程就ok了,需要是实现头尾的连接,并保持原来最初的位置

(1)寄包柜

题目

请添加图片描述

代码

#include<bits/stdc++.h>
using namespace std;
map<int,int>book[100001];
int main() {
	int n,q;
	cin>>n>>q;
	for(int l=0; l<q; l++) {
		int f,i,j,k;
		cin>>f;
		if(f==1) {
			cin>>i>>j>>k;
			book[i][j]=k;
		} 
		if(f==2) {
			cin>>i>>j;
			cout<<book[i][j]<<endl;
		}
	}
	return 0;
}

(2)括号序列

题目

请添加图片描述
请添加图片描述

代码

#include<bits/stdc++.h>
using namespace std;
int arr[105];
int main() {
	string s;
	cin>>s;
	for (int i=0; i<s.length(); i++) {
		if (s[i]==')') {
			for (int j=i-1; j>=0;j--) {
				if (s[j]=='('&&arr[j]==0) {
					arr[i]=arr[j]=1;
					break;
				} 
				else if(s[j]=='['&&arr[j]==0) break;
			}
		} 
		else if (s[i]==']') {
			for (int j=i-1; j>=0; j--) {
				if (s[j]=='['&&arr[j]==0) {
					arr[i]=arr[j]=1;
					break;
				} 
				else if(s[j]=='('&&arr[j]==0) break;
			}
		}
	}
	for (int i=0; i<s.length(); i++) {
		if (arr[i]==0) {
			if (s[i]=='('||s[i]==')') cout<<"()";
			else cout<<"[]";
		} 
		else cout<<s[i];
	}
	return 0;
}

(3)后缀表达式

题目

请添加图片描述

代码

#include<bits/stdc++.h>
using namespace std;
struct list_x {
	int next;
	int f;
};
int number(int x,int y,string s) {
	int sum=0;
	if(x!=0) {
		for(int i=y-1; i>=x+1; i--) {
			sum+=(s[i]-'0')*pow(10,y-1-i);
		}
	}
	if(x==0) {
		for(int i=y-1; i>=0; i--) {
			sum+=(s[i]-'0')*pow(10,y-1-i);
		}
	}
	return sum;
}
int main() {
	string s;
	cin>>s;
	list_x x[50];
	int temp=0;
	for(int i=0; i<s.length(); i++) {
		if(s[i]=='.') {
			x[temp].next=i;
			temp=i;
			x[temp].f=0;
			x[temp].next=0;
		}
		if(s[i]=='+'||s[i]=='-'||s[i]=='*'||s[i]=='/') {
			x[temp].next=i;
			temp=i;
			if(s[i]=='+')	x[temp].f=1;
			if(s[i]=='-')	x[temp].f=2;
			if(s[i]=='*')	x[temp].f=3;
			if(s[i]=='/')	x[temp].f=4;
			x[temp].next=0;
		}
		if(s[i]=='@')	break;
	}
	temp=x[0].next;
	int temp1=0;
	int stack[50];
	int top=0;
	while(temp!=0) {
		if(x[temp].f==0) {
			stack[top]=number(temp1,temp,s);
			top++;
		}
		if(x[temp].f!=0&&top>=2) {
			top--;
			if(x[temp].f==1)	stack[top-1]=stack[top-1]+stack[top];
			if(x[temp].f==2)	stack[top-1]=stack[top-1]-stack[top];
			if(x[temp].f==3)	stack[top-1]=stack[top-1]*stack[top];
			if(x[temp].f==4)	stack[top-1]=stack[top-1]/stack[top];
		}
		temp1=temp;
		temp=x[temp].next;
	}
	cout<<stack[0];
	return 0;
}

(4)队列安排

题目

请添加图片描述
请添加图片描述
请添加图片描述

代码

#include<bits/stdc++.h>
using namespace std;
struct student {
	int l,r;
	int f;
};
int main() {
	int N;
	cin>>N;
	student s[N+1];
	s[0].l=1,s[0].r=1,s[0].f=0;
	s[1].l=0,s[1].r=0,s[1].f=1;
	for(int i=2; i<=N; i++) {
		int k,p;
		cin>>k>>p;
		s[i].f=1;
		if(p==0) {
			s[i].r=k;
			s[i].l=s[k].l;
			s[s[k].l].r=i;
			s[k].l=i;
		}
		if(p==1) {
			s[i].l=k;
			s[i].r=s[k].r;
			s[s[k].r].l=i;
			s[k].r=i;
		}
	}
	int M;
	cin>>M;
	for(int i=0; i<M; i++) {
		int x;
		cin>>x;
		if(s[x].f==1) {
			s[s[x].l].r=s[x].r;
			s[s[x].r].l=s[x].l;
			s[x].f=0;
		}
	}
	int f=0;
	int temp=s[0].r;
	while(temp!=0) {
		if(f==1)	cout<<" ";
		cout<<temp;
		f=1;
		temp=s[temp].r;
	}
	return 0;
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值