【位运算&set容器的结合】

题面:
给你2e5个数每个数大小[-1e9,1e9],从中取几个数使得里面的数两两相差的绝对值都为2的幂次方,我们称这个集合为st集合。现在问最多取多少个数构成st集合,并输出这些数。 比如给你5个数 : 5 2848 3 7 0 最多取5 3 7出来满足条件,答案输出3和5 3 7。 (具体输出格式如样例所示

Example
Input
6
3 5 4 7 10 12
Output
3
7 3 5
Input
5
-1 2 5 8 11
Output
1
8

#include<bits/stdc++.h>
#define ll long long
#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 endl '\n'
#define mem(a) memset(a,0,sizeof(a))
#define IO ios::sync_with_stdio(false);cin.tie(0);
using namespace std;
const int INF=0x3f3f3f3f;
const int mod=1e9+7;
set<ll> q;
int main()
{
#ifdef Local
	freopen("../input.in", "r", stdin);
    freopen("../output.out", "w", stdout);
#endif
	ll n;cin>>n;
	ll a[n+5];
	for(ll i=1;i<=n;i++){
		cin>>a[i];
		q.insert(a[i]);
	}
	for(ll i=1;i<=n;i++){
		for(ll j=1;j<=2e9+5;j<<=1){
			if(q.count(a[i]+j)&&q.count(a[i]+2*j)){
				cout<<"3"<<endl<<a[i]<<" "<<a[i]+j<<" "<<a[i]+2*j<<endl;
				return 0;
			}
		}
	}
	for(ll i=1;i<=n;i++){
		for(ll j=1;j<=2e9+5;j<<=1){
			if(q.count(a[i]+j)){
				cout<<"2"<<endl<<a[i]<<" "<<a[i]+j<<endl;
				return 0;
			}
		}
	}
	cout<<"1"<<endl<<a[1]<<endl;
	return 0;
}

先讲讲思路吧。易知最大情况是3,最小是1。情况是3的时候 即前后相差同样的2^n倍;2的情况是单方面相差2 ^n;1的情况是除此之外。
先说说答案是3的情况吧:
首先我们需要建立一个set集合(因为它自带从小到大的排序功能,然后每次输入a[i]就把它insert进去。然后开2次for循环来遍历这些数,差值就是2^j,用.count()来查找set里的东西,一旦符合就ok啦!

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值