IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 数据结构与算法 -> 2018年第九届蓝桥杯 省赛 编程题题解 -> 正文阅读

[数据结构与算法]2018年第九届蓝桥杯 省赛 编程题题解

题目
A.递增三元组

题意: 给定三个数组,求有多少个三元组,满足Ai < Bj < Ck.
思路: 枚举中间那个数组,二分找即可。
(做过一次还是做错,太逆天了,每次都下意识枚举第一个数组,但是显然不满足单调性.)
时间复杂度: O(nlogn)
代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#include<set>
#include<map>
using namespace std;
#define mem(a,x) memset(a,x,sizeof(a))
#define fir(i,a,b) for(int i=a;i<=b;++i)
typedef long long ll;
typedef pair<int,int> PII;
int n,m,k,T;
vector<int> a,b,c;
ll ans = 0;
void solve()
{
	cin>>n;
	a = vector<int>(n); b = vector<int>(n); c = vector<int>(n);
	for(int i=0;i<n;++i) cin>>a[i];
	for(int i=0;i<n;++i) cin>>b[i];
	for(int i=0;i<n;++i) cin>>c[i];
	sort(a.begin(),a.end()); sort(b.begin(),b.end()); sort(c.begin(),c.end());
	for(int i=0;i<n;++i)
	{
		int idx1 = upper_bound(b.begin(),b.end(),a[i])-b.begin();
		if(idx1==n) continue;
		int idx2 = upper_bound(c.begin(),c.end(),b[idx1]) - c.begin();
		if(idx2==n) continue;
		ans += 1ll*(n-idx1)*(n-idx2);
	}
	cout<<ans;
}
signed main(void)
{
	ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
	solve();
	return 0;
} 

B.螺旋折线

题意: 给定一个螺旋折线,找到(x,y)是沿线走的哪个点。
思路: 终于自己独立做出来了,看来以前比现在还菜。这个是纯纯找规律,发现如果(i,i)对应的值是4ii.(我还拿错位相减推的,但是结合四个象限和平方就能观察出来)。|x|和|y|的最大值对应的那个数说明在(i,i)那一块,要么是x == i, x == -i,y == i,y == -i.分类讨论一下就好。
时间复杂度: O(1)
代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#include<set>
#include<map>
using namespace std;
#define mem(a,x) memset(a,x,sizeof(a))
#define fir(i,a,b) for(int i=a;i<=b;++i)
typedef long long ll;
typedef pair<int,int> PII;
int n,m,k,T;
ll x,y;
ll ans = 0;
void solve()
{
	cin>>x>>y;
	if(x == y && x >= 0)
	{
	    ans = 4ll*(x)*(x);
	}
	else
	{
		ll mx = max(abs(x),abs(y));
		ll n = mx;
	    ans = 4ll*(n) * (n);
		if(x == n)
		{
			ans += n-y;
		}
		else if(y==-n)
		{
			ans += 2*n;
			ans += n-x;
		}
		else if(y==n)
		{
			ans -= n-x;
		}
		else if(x==-n)
		{
			ans -= 2*n;
			ans -= n-y;
		}
	}
	cout<<ans<<endl;
}
int main(void)
{
    //	T = 1;
    cin>>T;
	while(T--)
	solve();
	return 0;
} 

C.日志统计

题意: 略。
思路: 把每个id的点赞排序,之后二分即可。也可以双指针,不过时间复杂度级别一样的,双指针写歪了还wa了两发。
时间复杂度: O(nlogn)
代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#include<set>
#include<queue>
#define mem(a,x) memset(a,x,sizeof(a))
#define fir(i,a,b) for(int i=a;i<=b;++i)
using namespace std;
const int N = 1e5+10;
typedef long long ll;
typedef pair<int,int> PII;
int n,m,k,T;
vector<int> va[N];
void solve()
{
	cin>>n>>m>>k;
	for(int i=0;i<n;++i)
	{
		int id; int x; cin>>id>>x;
		va[x].push_back(id);
	}
	for(int i=0;i<N;++i)
	{
		if(!va[i].size()) continue;
		sort(va[i].begin(),va[i].end());
		for(int j=0;j<va[i].size();++j)
		{
			int idx = lower_bound(va[i].begin(),va[i].end(),va[i][j]+m) - va[i].begin();
			idx--;
			int tot = idx-j+1;
			if(tot >= k) 
			{
				cout<<i<<"\n";
				break;
			}
		}
	}
}
int main(void)
{
	ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
	solve();
	return 0;
}
/*
7 10 2
0 1
0 10
10 10
10 1
9 1
100 3
100 3
*/
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#include<queue>
#include<set>
#include<map>
using namespace std;
const int N = 1e5+10;
typedef long long ll;
int n,m,k,T;
vector<int> va[N]; 
void solve()
{
	cin>>n>>m>>k;
	for(int i=0;i<n;++i)
	{
		int id,x; cin>>id>>x;
		va[x].push_back(id);
	}
	for(int i=0;i<N;++i)
	{
		if(!va[i].size()) continue;
		sort(va[i].begin(),va[i].end());
		int l = 0,r = 0;
		while(l < va[i].size() && r < va[i].size())
		{
			if(va[i][r]-va[i][l]>=m)
			{
				l++;
			}
			else
			{
				if(r-l+1 >= k) 
				{
					cout<<i<<"\n";
					break;
				}
				r++;
			}
		}
	}
}
int main(void)
{
	ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
	solve();
	return 0;
}

D.全球变暖

题意: 略。
思路: bfs判一下每个连通块是否满足条件。
时间复杂度: O(n)
代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#include<set>
#include<queue>
#define mem(a,x) memset(a,x,sizeof(a))
#define fir(i,a,b) for(int i=a;i<=b;++i)
using namespace std;
const int N = 1e5+10;
typedef long long ll;
typedef pair<int,int> PII;
int n,m,k,T;
char a[1002][1002];
int vis[1002][1002];
int dx[] = {-1,0,1,0};
int dy[] = {0,1,0,-1};
int ans = 0;
void bfs(int x,int y,int id)
{
	int cnt = 0;
	int tot = 0;
    queue<PII> q;
    q.push({x,y});
    vis[x][y] = id;
    while(q.size())
    {
    	PII tmp = q.front(); q.pop();
    	int x = tmp.first,y = tmp.second;
    	cnt++;
    	bool flag = 0;
    	for(int i=0;i<4;++i)
        {
        	int tx = x + dx[i];
        	int ty = y + dy[i];
        	if(tx<1||ty<1||tx>n||ty>n) continue;
        	if(vis[tx][ty]) continue;
        	if(a[tx][ty] == '.') {flag = 1; continue;}
        	vis[tx][ty] = id;
        	q.push({tx,ty});
		}
		if(flag) tot++;
	}
	if(tot == cnt) ans++;
}
void solve()
{
	cin>>n;
	for(int i=1;i<=n;++i)
	{
		for(int j=1;j<=n;++j)
		{
			cin>>a[i][j];
		}
	}
	int id = 0;
	for(int i=1;i<=n;++i)
	{
		for(int j=1;j<=n;++j)
		{
			if(!vis[i][j] && a[i][j] == '#')
			{
				bfs(i,j,++id);
			}
		}
	}
	cout<<ans;
}
int main(void)
{
	ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
	solve();
	return 0;
}
/*
7
.......
.##....
.##....
....##.
..####.
...###.
.......
*/

E.最大乘积

题意: 给定n个数,从中选出k个,使得乘积最大。
思路: 刚开始想复杂了,分类了很多情况。但是发现并不用(看了题解以后).
贪心就行。
(一) 如果都是负数并且k是奇数,结果只能是负数了。
(二) 否则说明存在非负数,就可以逆转正负,结果至少是个0.
如果k是奇数,把最大值先乘上,之后取出最小的两个数和最大的两个数比较乘积大小,类似归并,其实是贪心的思想了。(因为负数肯定两个最小的值乘起来大,我刚开始还想着分开放)
时间复杂度: O(nlogn)
代码:

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<vector>
#include<set>
#include<queue>
#define mem(a,x) memset(a,x,sizeof(a))
#define fir(i,a,b) for(int i=a;i<=b;++i)
using namespace std;
const int N = 1e5+10;
typedef long long ll;
typedef pair<int,int> PII;
int n,m,k,T;
const int mod = 1000000009;
ll ans = 1;
void solve()
{
	cin>>n>>k;
	vector<int> a(n);
	int cnt = 0;
	for(int i=0;i<n;++i)
	{
		cin>>a[i];
		if(a[i] < 0) cnt++;
	}
	sort(a.begin(),a.end());
	if(cnt == n) //全是负数
	{
		if(k & 1)
		{
		   for(int i=a.size()-1;i>=0;--i)
		   {
		       ans = ans * a[i] % mod;	
		   }	
		}
		else
		{
			for(int i=0;i<k;++i)
			{
				ans = ans * a[i] % mod;
			}
		}
		if(ans < 0) ans = -((-ans)%mod);
		cout<<ans; return ;
	}
	int l = 0,r = n-1;
	if(k & 1)
	{
		ans = ans * a[r--];
		k--;
	}
	while(k)
	{
	    ll t1 = a[l] * a[l+1];
	    ll t2 = a[r] * a[r-1];
	    if(t1 > t2)
	    {
	    	ans = t1 % mod * ans % mod;
	    	l += 2;
		}
		else
		{
			ans = t2 % mod * ans % mod;
			r -= 2;
		}
		k -= 2;
	}
	cout<<ans;
}
int main(void)
{
	ios::sync_with_stdio(false),cin.tie(0),cout.tie(0);
	solve();
	return 0;
}
/*
5 3
-100000
-10000
2
100000
10000
*/
  数据结构与算法 最新文章
【力扣106】 从中序与后续遍历序列构造二叉
leetcode 322 零钱兑换
哈希的应用:海量数据处理
动态规划|最短Hamilton路径
华为机试_HJ41 称砝码【中等】【menset】【
【C与数据结构】——寒假提高每日练习Day1
基础算法——堆排序
2023王道数据结构线性表--单链表课后习题部
LeetCode 之 反转链表的一部分
【题解】lintcode必刷50题<有效的括号序列
上一篇文章      下一篇文章      查看所有文章
加:2022-04-09 18:42:57  更:2022-04-09 18:45:36 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 9:48:38-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码