XTU 1236 Fraction (二分)

題目鏈接:http://202.197.224.59/OnlineJudge2/index.php/Problem/read/id/1236

題目大意:
給出一個0,1之間小數,求最接近該小數的分數,分母規定在1到1000。
注意題目有10000個數據。。。

解題思路:
預處理一個分數和對應的小數表並且排好序,按照題目要求,先按分數值大小排序,再按分子分母大小排,對於每次查詢進行二分查找這個表得到一個pos值,再枚舉該位置的1000到後1000個數,找出最接近的分數,就是答案。

Code:

/*   W          w           w        mm          mm             222222222       7777777777777    */
/*    W        w w         w        m  m        m  m          222        22              7777    */
/*    w        w w         w        m  m        m  m                     22              777     */
/*     w      w   w       w        m    m      m    m                    22              77      */
/*     w      w    w      w        m    m      m    m                 222                77      */
/*      w    w      w    w        m      m    m      m              222                  77      */
/*      w    w      w    w        m      m    m      m            222                    77      */
/*       w  w        w  w        m        m  m        m         222                      77      */
/*       w  w        w  w        m        m  m        m      222                         77      */
/*        ww          ww        m          mm          m     222222222222222             77      */

//#pragma comment(linker, "/STACK:102400000,102400000")
//C++
//int size = 256 << 20; // 256MB
//char *p = (char*)malloc(size) + size;
//__asm__("movl %0, %%esp\n" :: "r"(p));
//G++
#include<set>
#include<map>
#include<queue>
#include<stack>
#include<ctime>
#include<deque>
#include<cmath>
#include<vector>
#include<string>
#include<cctype>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<sstream>
#include<iostream>
#include<algorithm>
#define REP(i,s,t) for(int i=(s);i<=(t);i++)
#define REP2(i,t,s) for(int i=(t);i>=s;i--)

using namespace std;

typedef long long ll;
typedef unsigned long long ull;
typedef unsigned long ul;

int T;
double x;
int gcd(int x,int y)
{
  return x==0?y:gcd(y%x,x);
}
struct xxx
{
  double idx,idy;
  double res;
  xxx (double _idx=0,double _idy=0,double _res=0):idx(_idx),idy(_idy),res(_res){}
  bool operator < (const xxx &r)const
  {
    if((double)fabs(res-r.res)<1e-12)
    {
      if(idx==r.idx)
      {
        return idy<r.idy;
      }
      return idx<r.idx;
    }
    return res<r.res;
  }
};
bool vis[1000005];
vector<xxx>ans;
vector<double>a;
void fuck()
{
  ans.clear();
  for(double i=1;i<=1000;i++)
  {
    for(double j=0;j<=i;j++)
    {
      int k=gcd((int)i,(int)j);
      if(j>0)
      {
        ans.push_back(xxx(j/(double)k,i/(double)k,j/i));
      }
      else
      {
        ans.push_back(xxx(j,i,j/i));
      }
    }
  }
  sort(ans.begin(),ans.end());
  a.clear();
  for(int i=0;i<ans.size();i++)
  {
    a.push_back(ans[i].res);
  }
}
int main()
{
  #ifdef ONLINE_JUDGE
  #else
    freopen("test.in","r",stdin);
  #endif
  fuck();
  scanf("%d",&T);
  while(T--)
  {
    scanf("%lf",&x);
    int pos=lower_bound(a.begin(),a.end(),x)-a.begin();
    int p=pos;
    int d=1000;
    for(int i=-d;i<=d;i++)
    {
      if(pos+i<0||pos+i>a.size()-1)
      {
        continue;
      }
      if(fabs(a[pos+i]-x)<fabs(a[p]-x))
      {
        p=pos+i;
      }
    }
    printf("%d/%d\n",(int)ans[p].idx,(int)ans[p].idy);
  }
  return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章