codeforces 479d Long Jumps

题意:

让你根据所给的标尺上的刻度,能测量出 x 和 y。若不能,求出添加最少刻度的数量以满足要求。

思路:

没看清楚题目,以为是各个测量段可以叠加的,结果越想越复杂。

分类讨论。

最多添加2个刻度点。用map保存当前的已有点,每次判断的时候,以测量x为例,点的刻度加上x看看相加后的结果是否存在。存在即可测量出x;

1.原有刻度已经可以测量出x,y,添加0个点;

2.如果仅有一个点可以测量出来,直接把另一个点输出。添加1个点;

3.两个点现在都不能测量出来,寻找是否存在添加一个点后,使得该点与另外两个已存在的点距离分别为x 和 y,只添加一个点。 ( 否则,添加2个点,x , y)

code:

/* **********************************************
Created Time: 2014-10-20 9:35:26
File Name   : cf.cpp
*********************************************** */
//#pragma comment(linker, "/STACK:102400000,102400000")
#include <iostream>
#include <fstream>
#include <cstring>
#include <climits>
#include <deque>
#include <cmath>
#include <queue>
#include <stack>
#include <list>
#include <map>
#include <set>
#include <utility>
#include <sstream>
#include <complex>
#include <string>
#include <vector>
#include <cstdio>
#include <bitset>
#include <functional>
#include <algorithm>
using namespace std;
typedef long long LL;
const int MAXN = 1e5+5;
map <int, bool> mp;
int n, l, x, y;
int a[MAXN];
int main()
{
        cin>>n>>l>>x>>y;
        mp.clear();
        for(int i = 0;i < n; i++)
        {
                cin>>a[i];
                mp[a[i]] = true;
        }
        bool et1 = false , et2 = false;
        int cot = 0;
        for(int i = 0;i < n; i++)
        {
                int tmp = a[i] + x;
                if(tmp > l) break;
                if(mp.find(tmp) != mp.end())
                {
                        et1 = true;
                        cot++;
                        break;
                }
        }
        for(int i = 0;i < n; i++)
        {
                int tmp = a[i] + y;
                if(tmp > l) break;
                if(mp.find(tmp) != mp.end())
                {
                        et2 = true;
                        cot++;
                        break;
                }
        }
        //
        if(cot == 2)
        {
                cout<<"0"<<endl;
                return 0;
        }
        if(cot == 1)
        {
                int tt;
                if(!et1)
                {
                        cout<<"1"<<endl<<x<<endl;
                        return 0;
                }
                else
                {
                        cout<<"1"<<endl<<y<<endl;
                        return 0;
                }
        }
        //bool mark = false;
        int res;
        for(int i = 0;i < n; i++)
        {
                int tx[2] = {a[i]+x, a[i]-x};
                for(int i = 0;i < 2; i++)
                {
                        if(tx[i] >= 0 && tx[i] <= l)
                        {
                                int ty = tx[i]+y, ty2 = tx[i] - y;
                                //if(ty >= 0 && ty <= l)
                                if(mp.find(ty) != mp.end())
                                {
                                        res = tx[i];
                                        cout<<"1"<<endl<<res<<endl;
                                        return 0;
                                }
                                //if(ty2 >= 0 && ty2 <= l)
                                if(mp.find(ty2) != mp.end())
                                {
                                        res = tx[i];
                                        cout<<"1"<<endl<<res<<endl;
                                        return 0;
                                }
                        }
                }
        }
        cout<<"2"<<endl<<x<<" "<<y<<endl;
        return 0;
}


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值