快速讀入(出)/讀入(出)優化(模板)


一、前言

衆所周知:scanfcin快得多,printfcout快得多。這裏的優化思想就是運用getchar(putchar)scanf(printf)快的優勢寫一個模板,注意,這裏只是針對整數,浮點數目前不支持。

二、輸入

1.入門級的cin

cin >> a >> b;

2.普遍的scanf

scanf("%d%d", &a, &b);

3.關閉流同步的cin

ios::sync_with_stdio(false);  
cin >> a >> b;

4.讀入優化read

(1).讀入優化read,原理是將數字按照數位一個個讀進來(比如數字123)就會依次讀入 1, 2, 3,每次將數字乘10再加當前數字)

int read() {//'&'表示引用,也就是說x是一個實參,在函數中改變了x的值就意味着在外面x的值也會被改變
    int f = 1;//標記正負
    int x = 0;//結果
    char s = getchar();//讀入第一個字符
    while (!isdigit(s)) {//不是數字
        if (s == '-') //不能直接把f = -1,有可能輸入的不是'-'而是其它的東西
            f = -1;
        s = getchar(); //繼續讀
    }
    while (isdigit(s)) {//是數字(一旦不是數字就意味着輸入結束了)
        x = x * 10 + s - '0';
        s = getchar();
    }
    return x * f; //改變正負
}
int main() {
    a = read();
}

(2).上面這個只能讀入int,其它類型的不能讀入,故流出了下面這個版本(代碼的template <...是爲了能同時讀入多種類型變量(unsigned)int, longlong, short都行):

template <typename _Tp>
inline _Tp read(_Tp &x) {
    char ch = getchar(), sgn = 0; x = 0;
    while (ch ^ '-' && !isdigit(ch)) ch = getchar();
    if (ch == '-') ch = getchar(), sgn = 1;
    while (isdigit(ch)) x = x * 10 + ch - '0', ch = getchar();
    if (sgn) x = -x;
    return x;
}
int main() {
    b = read(a);
}

5.讀入優化fread

準備區域賽時發現fread表現更優秀(這裏和上頭差不多,只不過是一次性讀入一大串字符,gc()函數每調用一次返回一個字符,相當於上面的getchar()).

struct ios_in {
    inline char gc() {
        static char buf[MAXN], *l, *r;
        return (l == r) && (r = (l = buf) + fread(buf, 1, MAXN, stdin), l == r) ? EOF : *l++;
    }
    template <typename _Tp>
    inline ios_in & operator >> (_Tp &x) {
        static char ch, sgn;
        for (sgn = 0, ch = gc(); !isdigit(ch); ch = gc()) {
            if (!~ch) return *this;
            sgn |= ch == '-';
        }
        for (x = 0; isdigit(ch); ch = gc())
            x = (x << 1) + (x << 3) + (ch ^ '0');
        sgn && (x = -x);
        return *this;
    }
}Cin;
int main() {
    Cin >> a;
}

比較

C/C++幾種輸入方法的速度大致爲:cin<<scanf<cin()<read<<freadcin<<scanf<cin(關閉流同步)<read<<fread.

三、輸出

1.入門級的cout

cout << a << b;

2.普遍的printf

printf("%d%d", a, b);

3.關閉流同步的cout

ios::sync_with_stdio(false);  
cout << a << b;

4.讀出優化write

void write(int x) {
     if (x < 0) putchar('-'), x = -x;
     if (x > 9) write(x / 10);
     putchar(x % 10 + '0');
}
int main() {
    write(a);
}

5.數組優化

struct ios_out {
    template <typename _Tp>
    inline void operator << (_Tp &x) {
        char F[MAXN];
        _Tp tmp = x > 0 ? x : (putchar('-'), -x);
        int cnt = 0;
        while (tmp) {
            F[cnt++] = tmp % 10 + '0';
            tmp /= 10;
        }
        while (cnt) putchar(F[--cnt]);
    }
}Cout;
int main() {
    Cout << a;
}

比較

C/C++幾種輸入方法的速度大致爲:cout<<printf<cout()<write<cout<<printf<cout(關閉流同步)<write<數組優化.

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章