FastIO

· · 科技·工程

轻量化 IO

考场上可以手写的版本。

static char buf[1<<20],*buf1,*buf2;
#define gc() (buf1==buf2&&(buf2=(buf1=buf)+fread(buf,1,1<<20,stdin),buf1==buf2)?EOF:*buf1++)
//#define gc() getchar()
#define pc(x) putchar(x)
inline void rd(char *a,int &l)
{
    register char c=gc();l=0;
    while(c<'a'||'z'<c)c=gc();
    while('a'<=c&&c<='z')a[++l]=c,c=gc();
}
void wt(int x)
{
    if(x<=9)pc(x+'0');
    else wt(x/10),pc(x%10+'0');
}

多参数

自己写的板子。快读快输,接受多参数。

注意 static 编译很慢,调试的时候可以先注释掉。

static char buf[1<<20],*buf1,*buf2,out[1<<20],*obuf=out;
#define gc() (buf1==buf2&&(buf2=(buf1=buf)+fread(buf,1,1<<20,stdin),buf1==buf2)?EOF:*buf1++)
#define flush() (fwrite(out,1,obuf-out,stdout),obuf=out)
#define pc(x) ((obuf==out+(1<<20)?flush():0),*obuf++=(x))
struct flusher{~flusher(){flush();}}_;
template<typename T,typename...R>inline void rd(T &x)
{
    register char c=gc();int op(1);T v=0;
    while(c<'0'||'9'<c)op=c=='-'?-1:1,c=gc();
    while('0'<=c&&c<='9')v=(v<<1)+(v<<3)+(c^48),c=gc();
    x=v*op;
}
template<typename T,typename...R>inline void rd(T &x,R &...y){rd(x),rd(y...);}
template<typename T,typename...R>inline void wt(T x)
{
    static char q[40],*p=q;T v=x;
    if(v==0){pc('0');return;}
    if(v<0)pc('-'),v=-v;
    while(v)*p++=(v%10)^48,v/=10;
    while(p!=q)pc(*--p);
}
template<typename T,typename...R>inline void wt(T x,R...y){wt(x),wt(y...);}

读入字符串

使用指针。

inline void Read(char* str)
{
    char ch = gc();
    while(ch < 32 || ch > 126) ch = gc();
    while(32 <= ch && ch <= 126) *(str ++ ) = ch, ch = gc();
}

封装快读快写

更接近于 cincout 的使用。

代码长度缩短了。

几个调整输入方式的成员函数:

同样可以通过在本地宏定义 LOCAL 进行调试。

调用示例:

int main()
{
    char x, y[3];
    int a;
    unsigned b;
    IO.strline(); 
    IO >> x >> y >> a >> b;
    IO << x << IO.endl << y << IO.endl << a << IO.endl << b << IO.endl;
    return 0;
}

警告:可能出 bug,最好不要滥用。

目前浮点数的读入可能出一些精度问题。

代码

struct fast_IO{
    /***read***/
    char buf[1000000], *s = buf, *t = buf;
    inline char gc()
    {
        #ifdef LOCAL
        return getchar();
        #endif
        return s == t && (t = (s = buf) + fread(buf, 1, 1000000, stdin), s == t) ? EOF : *s ++ ;
    }

    // read a character
    int chtype = 0;
    inline void chnormal() {chtype = 0;}
    inline void chall() {chtype = 1;}
    inline void chdigit() {chtype = 2;}
    inline void chletter() {chtype = 3;}
    inline char chread()
    {
        char ch = gc();
        while(ch != EOF && ch <= 32) ch = gc();
        return ch;
    }
    inline char digitread()
    {
        char ch = gc();
        while(ch != EOF && (ch < '0' || ch > '9')) ch = gc();
        return ch;
    }
    inline char letterread()
    {
        char ch = gc();
        while(ch != EOF && !('A' <= ch && ch <= 'Z' || 'a' <= ch && ch <= 'z')) ch = gc();
        return ch;
    }

    // read a string
    int strtype = 0;
    inline void strnormal() {strtype = 0;}
    inline void strline() {strtype = 1;}
    inline void strread(char *s)
    {
        char ch = gc();
        while(ch <= 32) ch = gc();
        while(ch > 32) *s ++ = ch, ch = gc();
        *s = 0;
    }
    inline void lineread(char *s)
    {
        char ch = gc();
        while(ch < 32) ch = gc();
        while(ch >= 32) *s ++ = ch, ch = gc();
        *s = 0;
    }

    // read an integer
    int inttype = 0;
    inline void intnormal() {inttype = 0;}
    inline void intunsigned() {inttype = 1;}
    int lltype = 0;
    inline void llnormal() {lltype = 0;}
    inline void llunsigned() {lltype = 1;}
    template <typename T>
    inline void uread(T &x)
    {
        char ch = gc();
        x = 0;
        while(ch < '0' || ch > '9') ch = gc();
        while('0' <= ch && ch <= '9') x = (x << 1) + (x << 3) + (ch ^ 48), ch = gc();
    }
    template <typename T>
    inline void read(T &x)
    {
        char ch = gc();
        x = 0;
        bool f = 0;
        while(ch < '0' || ch > '9')
        {
            if(ch == '-') f = 1;
            ch = gc();
        }
        if(f) while('0' <= ch && ch <= '9') x = x * 10 - (ch ^ 48), ch = gc();
        else while('0' <= ch && ch <= '9') x = x * 10 + (ch ^ 48), ch = gc();
    }

    // read a real number
    template <typename T>
    inline void dread(T &x)
    {
        char ch = gc();
        x = 0;
        int f = 1;
        while(ch < '0' || ch > '9')
        {
            if(ch == '-') f = -1;
            ch = gc();
        }
        while('0' <= ch && ch <= '9') x = x * 10 + (ch ^ 48), ch = gc();
        if(ch == '.')
        {
            ch = gc();
            double p = 0.1;
            while('0' <= ch && ch <= '9') x += p * (ch ^ 48), ch = gc(), p *= 0.1;
        }
        x *= f;
    }

    inline fast_IO & operator >> (char &x)
    {
        switch(chtype)
        {
            case 0 : x = chread(); break ;
            case 1 : x = gc(); break ;
            case 2 : x = digitread(); break ;
            case 4 : x = letterread(); break ;
            default : break ;
        }
        return *this;
    }
    inline fast_IO & operator >> (char *x)
    {
        strtype ? lineread(x) : strread(x);
        return *this;
    }
    inline fast_IO & operator >> (string &x)
    {
        static char buf[1000005];
        strtype ? lineread(buf) : strread(buf);
        return x = buf, *this;
    }
    inline fast_IO & operator >> (int &x)
    {
        inttype ? uread(x) : read(x);
        return *this;
    }
    inline fast_IO & operator >> (unsigned &x)
    {
        return uread(x), *this;
    }
    inline fast_IO & operator >> (long long &x)
    {
        lltype ? uread(x) : read(x);
        return *this;
    }
    inline fast_IO & operator >> (unsigned long long &x)
    {
        return read(x), *this;
    }
    inline fast_IO & operator >> (__int128 &x)
    {
        lltype ? read(x) : read(x);
        return *this;
    }
    inline fast_IO & operator >> (unsigned __int128 &x)
    {
        return read(x), *this;
    }
    inline fast_IO & operator >> (float &x)
    {
        return dread(x), *this;
    }
    inline fast_IO & operator >> (double &x)
    {
        return dread(x), *this;
    }
    inline fast_IO & operator >> (long double &x)
    {
        return dread(x), *this;
    }
    inline fast_IO & operator >> (__float128 &x)
    {
        return dread(x), *this;
    }

    /***write***/
    char obuf[1000000], *p = obuf;
    const char endl = '\n';
    inline void pc(char x)
    {
        p - obuf < 1000000 ? (*p ++ = x) : (fwrite(obuf, p - obuf, 1, stdout), p = obuf, *p ++ = x);
    }
    inline ~fast_IO() {fwrite(obuf, p - obuf, 1, stdout);}
    template <typename T>
    inline void write(T x)
    {
        if(!x) return pc(48);
        int len = 0;
        static char c[40];
        if(x < 0) pc('-'), x = -x;
        while(x) c[ ++ len] = (x % 10) ^ 48, x /= 10;
        while(len) pc(c[len -- ]);
    }
    inline fast_IO & operator << (int x)
    {
        return write(x), *this;
    }
    inline fast_IO & operator << (unsigned x)
    {
        return write(x), *this;
    }
    inline fast_IO & operator << (long long x)
    {
        return write(x), *this;
    }
    inline fast_IO & operator << (unsigned long long x)
    {
        return write(x), *this;
    }
    inline fast_IO & operator << (__int128 x)
    {
        return write(x), *this;
    }
    inline fast_IO & operator << (unsigned __int128 x)
    {
        return write(x), *this;
    }
    inline fast_IO & operator << (char x)
    {
        return pc(x), *this;
    }
    inline fast_IO & operator << (char *x)
    {
        while(*x) pc(*x ++ );
        return *this;
    }
    inline fast_IO & operator << (string x)
    {
        for(char i : x) pc(i);
        return *this;
    }
}IO;