什么玩意?快读快写浮点型数据?

来源:互联网 发布:nginx 判断是否有参数 编辑:程序博客网 时间:2024/05/21 17:57

我下午花了一个小时写了一个什么玩意?居然能过poj1064 Cable master?大家都知道有整型数据快读快写.如下:

//我写的比较骚.这么写比较简单,仅限非负整数.inline int read(){int x=0;char c=getchar();for (;!isdigit(c);c=getchar();for (;isdigit(c);c=getchar()) x=x*10+c-'0';return x;}//快速输出有两种写法:void write(int x)//递归{if (x>9) write(x/10);putchar(x%10+48);}inline void write(int x)//非递归{register int bit[20],i,p=0;if (x==0) {putchar('0');return;}//特判0,递归输出不用判.这里由于相当于把它转化成10进制整数逐位输出,故需要判0for (;x;x/=10) bit[++p]=x%10;for (i=p;i>0;--i) putchar(bit[i]+48);}//递归代码短.当然非递归也长不到哪里去.

然后就是非常滑稽的浮点型快读了.

inline void read(double &r){double x=0,t=0;int s=0,f=1;char c=getchar();//x代表整数部分,t代表小数部分for (;!isdigit(c);c=getchar())   {  if (c=='-') f=-1;//读到负号就改变之  if (c=='.') goto readt;//看到小数点,直接读小数部分  }for (;isdigit(c)&&c!='.';c=getchar()) x=x*10+c-'0';//整数部分readt:for (;c=='.';c=getchar());//跳过小数点 for (;isdigit(c);c=getchar()) t=t*10+c-'0',++s;//读小数部分,s代表小数有几位r=(x+t/pow(10,s))*f;//t除以10的s次方后变成小数部分}inline void read(int &x)//整型快读,注意这里是void有自变量{x=0;char c=getchar();for (;!isdigit(c);c=getchar());for (;isdigit(c);c=getchar()) x=x*10+c-'0';}inline void dwrite(ll x)//用于输出整数部分{if (x==0) {putchar(48);return;}int bit[20],p=0,i;for (;x;x/=10) bit[++p]=x%10;for (i=p;i>0;--i) putchar(bit[i]+48);}inline void write(double x,int k=6)//不加位数,默认保留小数点后6位小数{static int n=pow(10,k);//和读入相反,这里我无法直接转化小数部分,先乘以n,就可以当做整数处理if (x==0)//x=0,保留的k位不断输出0;   {  putchar('0'),putchar('.');  for (int i=1;i<=k;++i) putchar('0');  return;  }if (x<0) putchar('-'),x=-x;//负数ll y=(ll)(x*n)%n;x=(ll)x;//y表小数部分,x*n之后把小数部分截去再对n取余就可以得到需要保留的小数部分.dwrite(x),putchar('.');//输出整数部分和小数点int bit[10],p=0,i;for (;p<k;y/=10) bit[++p]=y%10;//必须严格按照k位保留,否则就gg了for (i=p;i>0;i--) putchar(bit[i]+48);}

好tm有意思.以下是poj1064的题解.具体的话就是二分答案.

#include<cstdio>#include<cctype>#include<cmath>using namespace std;typedef long long ll;inline void read(double &r){double x=0,t=0;int s=0,f=1;char c=getchar();for (;!isdigit(c);c=getchar())   {  if (c=='-') f=-1;  if (c=='.') goto readt;  }for (;isdigit(c)&&c!='.';c=getchar()) x=x*10+c-'0';readt:for (;c=='.';c=getchar()); for (;isdigit(c);c=getchar()) t=t*10+c-'0',++s;r=(x+t/pow(10,s))*f;}inline void read(int &x){x=0;char c=getchar();for (;!isdigit(c);c=getchar());for (;isdigit(c);c=getchar()) x=x*10+c-'0';}inline void dwrite(ll x){if (x==0) {putchar(48);return;}int bit[20],p=0,i;for (;x;x/=10) bit[++p]=x%10;for (i=p;i>0;--i) putchar(bit[i]+48);}inline void write(double x,int k=6){static int n=pow(10,k);if (x==0)   {  putchar('0'),putchar('.');  for (int i=1;i<=k;++i) putchar('0');  return;  }if (x<0) putchar('-'),x=-x;ll y=(ll)(x*n)%n;x=(ll)x;dwrite(x),putchar('.');int bit[10],p=0,i;for (;p<k;y/=10) bit[++p]=y%10;for (i=p;i>0;i--) putchar(bit[i]+48);}int a[10000],n,k,i,l,r=1e7+1,m,s;double f;int main(){read(n),read(k);for (i=0;i<n;++i) read(f),a[i]=int((f+1e-6)*100);for (;l!=r-1;)  {  m=(l+r)/2;s=0;  for (i=0;i<n;++i) s+=a[i]/m;  s>=k?l=m:r=m;  }write(1.*l/100.,2);}/*//虽然我的快读快输是正确的,但和原代码的时间区别并不大,可能我白打了.#include<cstdio>int a[10000],n,k,i,l,r=1e7+1,m,s;double f;int main(){scanf("%d%d",&n,&k);for (i=0;i<n;i++) scanf("%lf",&f),a[i]=int((f+1e-6)*100);for (;l!=r-1;)  {  m=(l+r)/2;s=0;  for (i=0;i<n;i++) s+=a[i]/m;  s>=k?l=m:r=m;  }printf("%.2f",1.*l/100.);}*/

然而事实是我读入并输出100000个数用scanf和printf要0.5s,用快读快写只需要0.16s.可能还是我的错觉吧.

原创粉丝点击