poj2674浅谈

题目大意是,在一个一维的世界里有N个居民在一条直线上的不同位置,他们以恒定的速度大小,速度方向可能不同进行运动,相遇后会返回,问给定线段的长度l,速度v,求最后一个走出这个范围的居民是谁,用时多少。    

举个例子,我们可以现象一下几个质量相同刚体(忽略他们的半径)在同一直线上运动,速度方向可能不同,所以会发生弹性碰撞,假设没有任何能量损耗的话,碰撞后是彼此交换速度后返回的,如果求在t时刻,这些球的位置该如何求。因为相遇后彼此交换了速度后返回,所以从表面上看起来碰撞后各个球还是继续沿着原来的方向运动,所以可以求出t时刻这些刚体的分散在的位置,但是不能对上号,因为实际上发生碰撞后会返回的,但是注意一个细节就是不管这些球如何碰撞多少次,他们之间的相对顺序是不会变化的,所以对求出来的位置进行排个序就可以对上号了


分析出这个思想不难,但很多人wa在细节上。最后的结果是截取小数而不是四舍五入,这点需要注意。

下面附上我的ac代码

#include <iostream>
#include<math.h>
#include<algorithm>
#include <iomanip>
#include<stdio.h>
#define N 33000
using namespace std;
typedef struct
{
    char direct;
    double pos;
    string name;
}People;
bool cmp(const People &a,const People &b)
{
    return a.pos<b.pos;
}
People p[N];
int n;

int main()
{
    while(cin>>n&&n)
    {
         int z=0,i=0;
            double s=0.0,s1=0.0;
            double L,v;
            cin>>L>>v;
            int k=0,num=0,d=0;
            for(i=0;i<n;i++)
            {
                char ch=getchar();
                scanf("%c%lf",&p[i].direct,&p[i].pos);
                cin>>p[i].name;
            }
                //cin>>p[i].direct>>p[i].pos>>p[i].name;
            sort(p,p+n,cmp);
            for(i=0;i<n;i++)
            {
                if(p[i].direct=='p'||p[i].direct=='P')
                    s1=L-p[i].pos;
                else
                    s1=p[i].pos;
                if(s<s1)
                {
                    s=s1;
                    k=i;
                }
            }
            if(p[k].direct=='p'||p[k].direct=='P')
            {
                for(i=k+1;i<n;i++)
                {
                    if(p[i].direct=='n'||p[i].direct=='N')
                        num++;
                }
                d=k+num;
            }
            else
            {
                for(i=0;i<k;i++)
                {
                    if(p[i].direct=='p'||p[i].direct=='P')
                        num++;
                }
                d=k-num;
            }
            cout << setw(13) << fixed << setprecision(2) << (int)(s/v * 100) / 100.0 << ' ' << p[d].name <<endl;

    }
    return 0;
}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值