日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程语言 > c/c++ >内容正文

c/c++

C++输入、输出优化模板整理

發(fā)布時間:2024/4/11 c/c++ 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 C++输入、输出优化模板整理 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

前言

對于在信息學(xué)競賽中逐漸深入學(xué)習(xí)的C++選手們,會發(fā)現(xiàn)有些題目的輸入輸出量特別大,有時可能一道題讀入完你就TLE了。那么怎么辦呢?少用cin或者cout,因?yàn)槿绻銓in或者cout沒有進(jìn)行一些優(yōu)化的話,它會跑的很慢,所以你如果不會輸入輸出優(yōu)化的話,那就乖乖用scanf吧,這樣會相對快一點(diǎn)。
但是呢,scanf速度還是不夠快,那怎么辦呢?那就用輸入輸出優(yōu)化吧!

前置知識

getchar是讀入函數(shù)的一種。它從標(biāo)準(zhǔn)輸入里讀取下一個字符,相當(dāng)于getc(stdin)。返回類型為int型,為用戶輸入的ASCII碼,出錯返回-1
引用自 百度百科·getchar (計算機(jī)語言函數(shù))

看了度娘上的定義,你大概知道getchar()這個函數(shù)的定義了吧。然后呢,度娘里沒說,這個getchar()還是很快的呢,與它對應(yīng)的還有一個putchar(),于是呢我們就可以用它來進(jìn)行輸入輸出優(yōu)化啦
(頭文件是cstdio)

isdigit是計算機(jī)C(C++)語言中的一個函數(shù),主要用于檢查參數(shù)是否為十進(jìn)制數(shù)字字符。用于判斷字符c是否為數(shù)字,當(dāng)c為數(shù)字0~9時,返回非零值,否則返回零。 可以用一個字符數(shù)組循環(huán)判斷每一項(xiàng)是否為數(shù)字。

嗯,這個isdigit()能判斷一個字符是不是數(shù)字,好像很有用呢,那就當(dāng)一個前置知識吧
(頭文件是cctype)

輸入輸出優(yōu)化的簡單版

void read(int&x)//只能讀入非負(fù)整數(shù) {char cu=getchar();x=0;//x置0,防止x有初始值while(!isdigit(cu))cu=getchar();while(isdigit(cu))x=x*10+cu-'0',cu=getchar(); } void read(int&x)//能讀入正、負(fù)整數(shù)和0 {char cu=getchar();x=0;bool fla=0;//記錄這個數(shù)是不是負(fù)數(shù)while(!isdigit(cu)){if(cu=='-')fla=1;cu=getchar();}while(isdigit(cu))x=x*10+cu-'0',cu=getchar();if(fla)x=-x; } //以上2個函數(shù)的用法為:對一個整型a,read(a)即可 void print(int x)//只能輸出非負(fù)整數(shù) {if(x>=10)print(x/10);putchar(x%10+'0'); } void print(int x)//能輸出正、負(fù)整數(shù)和0 {if(x<0)x=-x,putchar('\n');if(x>=10)print(x/10);putchar(x%10+'0'); } //以上2個函數(shù)的用法為:對一個整型a,print(a)即可

這樣你就會發(fā)現(xiàn),你的輸入輸出快樂很多,如果算法相同,輸入輸出量較大,速度優(yōu)勢會比較明顯呢。
嗯,好,如果你看懂了上面的代碼,那我就貼一波我自己用的代碼(加了一波優(yōu)化,不要問我什么意思,有些關(guān)鍵詞如果不知道就自己去查吧)

template <typename T> inline void read(T&x) {char cu=getchar();x=0;bool fla=0;while(!isdigit(cu)){if(cu=='-')fla=1;cu=getchar();}while(isdigit(cu))x=x*10+cu-'0',cu=getchar();if(fla)x=-x; } template <typename T> void printe(const T x) {if(x>=10)printe(x/10);putchar(x%10+'0'); } template <typename T> inline void print(const T x) {if(x<0)putchar('-'),printe(-x);else printe(x); }

溫馨提醒
使用這份輸入輸出代碼時請不要用它來讀入小數(shù)、字符串之類的(因?yàn)檫@份代碼是讀整型的啊),還有如果你不得已還要用其它的東西,那請你謹(jǐn)慎使用,因?yàn)檫@份讀優(yōu)可能會吃掉你的下個字符(有可能是換行符)。當(dāng)然你要是完全理解了,當(dāng)然可以使用啦

輸入輸出優(yōu)化的升級組件

用了讀優(yōu)之后程序讀入的飛快呢對吧。
然后呢,我想告訴你的是,你還是會在輸入速度上被碾壓,為什么呢?因?yàn)檫€可以繼續(xù)優(yōu)化哦
請看getchar()的函數(shù)內(nèi)容

int getchar(void) {static char buf[BUFSIZ];static char* bb=buf;static int n=0;if(n==0){n=read(0,buf,BUFSIZ);bb=buf;}return(--n>=0)?(unsigned char)*bb++:EOF; }

是不是有優(yōu)化的空間呢,用fread,一次多讀一些東西就快了,自己實(shí)現(xiàn),自然會比自帶的快呢(C++自帶的會因?yàn)榭紤]一些安全問題而變慢)
具體怎么優(yōu)化呢?看下面

namespace fast_IO {const int IN_LEN=10000000,OUT_LEN=10000000;char ibuf[IN_LEN],obuf[OUT_LEN],*ih=ibuf+IN_LEN,*oh=obuf,*lastin=ibuf+IN_LEN,*lastout=obuf+OUT_LEN-1;inline char getchar_(){return (ih==lastin)&&(lastin=(ih=ibuf)+fread(ibuf,1,IN_LEN,stdin),ih==lastin)?EOF:*ih++;}inline void putchar_(const char x){if(oh==lastout)fwrite(obuf,1,oh-obuf,stdout),oh=obuf;*oh++=x;}inline void flush(){fwrite(obuf,1,oh-obuf,stdout);} } using namespace fast_IO; #define getchar() getchar_() #define putchar(x) putchar_((x)) int main() {return flush(),0;//別忘了這個flush哦,放在這里是不會出問題的,要是你沒打那可就不能用這個優(yōu)化了 }

前面那一段要放在程序的最前面,然后還要說一件事,
#define getchar() getchar_()、
#define putchar(x) putchar_((x))
最好在自己調(diào)試的時候注釋掉,或者你用文件輸入輸出(freopen),否則你會發(fā)現(xiàn)你的程序會一直顯示等你輸入
update by 2019/1/2:其實(shí)還有個不用注釋掉的方法就是在輸入的最后輸入Ctrl+z然后Enter就可以了

總結(jié)

在C++中,輸入輸出有很多優(yōu)化,這只是一種,但又很有效。不過呢,要用的話最好要自己理解,否則可能會出問題,幾個注意事項(xiàng):

  • namespace fast_IO 那一段要打在最前面
  • read()、print()只能輸入輸出整數(shù)
  • 用read()、print()的時候用其它輸入輸出方式(cin、cout、gets()、scanf、printf、puts())要謹(jǐn)慎使用,用namespace fast_IO的時候禁止使用其它輸入輸出方式
  • 使用namespace fast_IO要注意內(nèi)存問題,那里面有一個很大的char數(shù)組,小心MLE
    最后貼出所有輸入輸出整合在一起的代碼
#include<cstdio> #include<cctype> namespace fast_IO {const int IN_LEN=10000000,OUT_LEN=10000000;char ibuf[IN_LEN],obuf[OUT_LEN],*ih=ibuf+IN_LEN,*oh=obuf,*lastin=ibuf+IN_LEN,*lastout=obuf+OUT_LEN-1;inline char getchar_(){return (ih==lastin)&&(lastin=(ih=ibuf)+fread(ibuf,1,IN_LEN,stdin),ih==lastin)?EOF:*ih++;}inline void putchar_(const char x){if(oh==lastout)fwrite(obuf,1,oh-obuf,stdout),oh=obuf;*oh++=x;}inline void flush(){fwrite(obuf,1,oh-obuf,stdout);} } using namespace fast_IO; #define getchar() getchar_() #define putchar(x) putchar_((x)) template <typename T> inline void read(T&x) {char cu=getchar();x=0;bool fla=0;while(!isdigit(cu)){if(cu=='-')fla=1;cu=getchar();}while(isdigit(cu))x=x*10+cu-'0',cu=getchar();if(fla)x=-x; } template <typename T> void printe(const T x) {if(x>=10)printe(x/10);putchar(x%10+'0'); } template <typename T> inline void print(const T x) {if(x<0)putchar('-'),printe(-x);else printe(x); } int main() {return flush(),0; }

大家學(xué)一下輸入輸出優(yōu)化,能讓自己的程序跑的更快哦
update by 2019/1/2:對讀優(yōu)進(jìn)行了部分壓行和更新,之前的那份的fread部分有小bug

總結(jié)

以上是生活随笔為你收集整理的C++输入、输出优化模板整理的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。