兩種將字符串轉(zhuǎn)換成浮點(diǎn)數(shù)的方法
方法一:
char szString[] = "-2876.99812376443";
double db1;
db1 = atof(szString);
printf("atof result:\n");
printf("%f %.12f %.2f %e %E\n", db1, db1, db1, db1, db1);
printf("%.1e %.1E %.18e %.18E\n", db1, db1, db1, db1);
方法二:
char szString2[] = "-2876.99812376443";
double db2;
sscanf(szString2, "%lf", &db2);
printf("\nsscanf result:\n");
printf("%f %.12f %.2f %e %E\n", db2, db2, db2, db2, db2);
printf("%.1e %.1E %.18e %.18E\n", db2, db2, db2, db2);
這兩種方法可以得到一模一樣的輸出!輸出如下:
atof result:
-2876.998124 -2876.998123764430 -2877.00 -2.876998e+003 -2.876998E+003
-2.9e+003 -2.9E+003 -2.876998123764430100e+003 -2.876998123764430100E+003
sscanf result:
-2876.998124 -2876.998123764430 -2877.00 -2.876998e+003 -2.876998E+003
-2.9e+003 -2.9E+003 -2.876998123764430100e+003 -2.876998123764430100E+003
很多人對(duì)sscanf家族的函數(shù)不太了解,我想把sscanf家族的函數(shù)具體用法寫(xiě)出來(lái),考試.大希望大家可以共同進(jìn)步,有什么不對(duì)的地方歡迎提出來(lái)。先瞄下該家族的一些函數(shù)原型:
// 從鍵盤(pán)輸入數(shù)據(jù)到變量
int scanf(char *format,...);
// 從字符串輸入數(shù)據(jù)到變量,如下相同
int sscanf(const char *buffer, const char *format, ... );
int _sscanf_l(const char *buffer, const char *format, locale_t locale, ... );
int swscanf(const wchar_t *buffer,const wchar_t *format, ... );
int _swscanf_l(const wchar_t *buffer,const wchar_t *format,locale_t locale, ... );
下面我們只看看標(biāo)準(zhǔn)形式的sscanf函數(shù):
int sscanf(const char *buffer, const char *format, ... );
先說(shuō)說(shuō)關(guān)于它的返回值的問(wèn)題,庫(kù)函數(shù)幾乎都是有返回值的,有些人可能很奇怪,怎么很少人用過(guò)sscanf的返回值呢?sscanf會(huì)返回成功接收到的變量數(shù)量的值。比如sscanf("3.14159","%f",&pi);返回值是1。
測(cè)試如下程序:
#include
int main ()
{
int a;
printf ("%d",scanf("%d\n",&a));
return 0;
}
如果你開(kāi)始就輸入回車(chē),程序會(huì)繼續(xù)等待你輸入,因?yàn)樵谳斎霐?shù)字的時(shí)候,scanf會(huì)跳過(guò)空白字符。the c programming language上說(shuō),scanf實(shí)際上是用getchar()接受由數(shù)字組成的字符串,再轉(zhuǎn)換成數(shù)字。如果我輸入ctrl-z(unix上是ctrl-d)則會(huì)返回-1(隨編譯器而定).這實(shí)際上就是常量EOF的值,也就是所謂的返回eof。如果我鍵入的不是數(shù)字返回值就是0。但是如果我輸入浮點(diǎn)數(shù),又會(huì)怎么樣呢?我舉的例子中同樣會(huì)返回1,但是緩沖區(qū)會(huì)留下垃圾,如果是scanf("%d%d",&a,&b);則會(huì)出錯(cuò)。這是可以使用一個(gè)庫(kù)函數(shù)fflush(stdin)來(lái)清除緩沖。不過(guò)貌似雨中飛燕大姐說(shuō)這個(gè)用法是非標(biāo)準(zhǔn)的。K&R,只是說(shuō)行為沒(méi)有定義,但我們可以使用while((c=getchar())!='\n'&&c!=EOF);同樣可以清除后面的垃圾scanf的格式匹配還是比較簡(jiǎn)單,一定要記住的就是普通變量一定要加上&,否則編譯器無(wú)法檢測(cè)錯(cuò)誤,但運(yùn)行肯定會(huì)段錯(cuò)誤。
代碼及意義
%a讀浮點(diǎn)值(僅適用于 C99)
%A讀浮點(diǎn)值(僅適用于 C99)
%c 讀單字符
%d 讀十進(jìn)制整數(shù)
%i 讀十進(jìn)制、八進(jìn)制、十六進(jìn)制整數(shù)
%e 讀浮點(diǎn)數(shù)
%E 讀浮點(diǎn)數(shù)
%f 讀浮點(diǎn)數(shù)
%F 讀浮點(diǎn)數(shù)(僅適用于 C99)
%g 讀浮點(diǎn)數(shù)
%G 讀浮點(diǎn)數(shù)
%o 讀八進(jìn)制數(shù)
%s 讀字符串
%x 讀十六進(jìn)制數(shù)
%X 讀十六進(jìn)制數(shù)
%p 讀指針值
%n 至此已讀入值的等價(jià)字符數(shù)
%u 讀無(wú)符號(hào)十進(jìn)制整數(shù)
%[ ] 掃描字符集合
%%讀 % 符號(hào)(百分號(hào))
前面都很簡(jiǎn)單,%p,%n很少用到,跳過(guò)。要輸入%必須要在前面再加一個(gè)%,重點(diǎn)來(lái)談?wù)?s和%[]。%s是讀入一個(gè)數(shù)組,他與gets的區(qū)別就在于%s會(huì)以任何的空字符結(jié)束,而gets是回車(chē)結(jié)束。同樣%s前可以加數(shù)字,表示只讀多少個(gè)。ANSI C 標(biāo)準(zhǔn)向 scanf() 增加了一種新特性,稱(chēng)為掃描集(scanset)。 掃描集定義一個(gè)字符集合,可由 scanf() 讀入其中允許的字符并賦給對(duì)應(yīng)字符數(shù)組。 掃描集合由一對(duì)方括號(hào)中的一串字符定義,左方括號(hào)前必須綴以百分號(hào)。 例如,以下的掃描集使 scanf() 讀入字符 A、B 和 C:
%[ABC]
使用掃描集時(shí),scanf() 連續(xù)吃進(jìn)集合中的字符并放入對(duì)應(yīng)的字符數(shù)組,直到發(fā)現(xiàn)不在集合中的字符為止(即掃描集僅讀匹配的字符)。返回時(shí),數(shù)組中放置以 null 結(jié)尾、由讀入字符組成的字符串。對(duì)于許多實(shí)現(xiàn)來(lái)說(shuō),用連字符可以說(shuō)明一個(gè)范圍。 例如,以下掃描集使 scanf() 接受字母 A 到 Z:
%[A-Z]
重要的是要注意掃描集是區(qū)分大小寫(xiě)的。因此,希望掃描大、小寫(xiě)字符時(shí),應(yīng)該分別說(shuō)明大、小寫(xiě)字母。對(duì)于%[]還可以用^+任意字符(包括eof)來(lái)結(jié)束字符串的輸入。比如%[^EOF]就是直到有EOF輸入,字符串才中止。但一定要記住就是c語(yǔ)言是緩沖輸入,即使你%[^a],再你輸入回車(chē)之前輸入多少的a都是不可能結(jié)束的。%s的輸入會(huì)跳過(guò)空白字符,但是%c則不會(huì)。這也就是
scanf("%d", &h);
scanf("%c", &c);
如果這寫(xiě)的話,變量c放的一定是回車(chē)。如果想實(shí)現(xiàn)這種輸入,可以在兩個(gè)語(yǔ)句之間加入一個(gè)getchar(),他可以吃掉這個(gè)回車(chē),也可用scanf("%d %c",&h,&c);來(lái)做,再輸入數(shù)字后加一個(gè)空格。就可以了但千萬(wàn)別用scanf("%d\n", &h); K&R說(shuō)的十分清楚,任何非格式化的字符都需要完全匹配。意味著,只有輸入數(shù)字后面再加\n才是合法的。還有就是*加在任何項(xiàng)的前面表示該項(xiàng)不符值。
方法一:
char szString[] = "-2876.99812376443";
double db1;
db1 = atof(szString);
printf("atof result:\n");
printf("%f %.12f %.2f %e %E\n", db1, db1, db1, db1, db1);
printf("%.1e %.1E %.18e %.18E\n", db1, db1, db1, db1);
方法二:
char szString2[] = "-2876.99812376443";
double db2;
sscanf(szString2, "%lf", &db2);
printf("\nsscanf result:\n");
printf("%f %.12f %.2f %e %E\n", db2, db2, db2, db2, db2);
printf("%.1e %.1E %.18e %.18E\n", db2, db2, db2, db2);
這兩種方法可以得到一模一樣的輸出!輸出如下:
atof result:
-2876.998124 -2876.998123764430 -2877.00 -2.876998e+003 -2.876998E+003
-2.9e+003 -2.9E+003 -2.876998123764430100e+003 -2.876998123764430100E+003
sscanf result:
-2876.998124 -2876.998123764430 -2877.00 -2.876998e+003 -2.876998E+003
-2.9e+003 -2.9E+003 -2.876998123764430100e+003 -2.876998123764430100E+003
很多人對(duì)sscanf家族的函數(shù)不太了解,我想把sscanf家族的函數(shù)具體用法寫(xiě)出來(lái),考試.大希望大家可以共同進(jìn)步,有什么不對(duì)的地方歡迎提出來(lái)。先瞄下該家族的一些函數(shù)原型:
// 從鍵盤(pán)輸入數(shù)據(jù)到變量
int scanf(char *format,...);
// 從字符串輸入數(shù)據(jù)到變量,如下相同
int sscanf(const char *buffer, const char *format, ... );
int _sscanf_l(const char *buffer, const char *format, locale_t locale, ... );
int swscanf(const wchar_t *buffer,const wchar_t *format, ... );
int _swscanf_l(const wchar_t *buffer,const wchar_t *format,locale_t locale, ... );
下面我們只看看標(biāo)準(zhǔn)形式的sscanf函數(shù):
int sscanf(const char *buffer, const char *format, ... );
先說(shuō)說(shuō)關(guān)于它的返回值的問(wèn)題,庫(kù)函數(shù)幾乎都是有返回值的,有些人可能很奇怪,怎么很少人用過(guò)sscanf的返回值呢?sscanf會(huì)返回成功接收到的變量數(shù)量的值。比如sscanf("3.14159","%f",&pi);返回值是1。
測(cè)試如下程序:
#include
int main ()
{
int a;
printf ("%d",scanf("%d\n",&a));
return 0;
}
如果你開(kāi)始就輸入回車(chē),程序會(huì)繼續(xù)等待你輸入,因?yàn)樵谳斎霐?shù)字的時(shí)候,scanf會(huì)跳過(guò)空白字符。the c programming language上說(shuō),scanf實(shí)際上是用getchar()接受由數(shù)字組成的字符串,再轉(zhuǎn)換成數(shù)字。如果我輸入ctrl-z(unix上是ctrl-d)則會(huì)返回-1(隨編譯器而定).這實(shí)際上就是常量EOF的值,也就是所謂的返回eof。如果我鍵入的不是數(shù)字返回值就是0。但是如果我輸入浮點(diǎn)數(shù),又會(huì)怎么樣呢?我舉的例子中同樣會(huì)返回1,但是緩沖區(qū)會(huì)留下垃圾,如果是scanf("%d%d",&a,&b);則會(huì)出錯(cuò)。這是可以使用一個(gè)庫(kù)函數(shù)fflush(stdin)來(lái)清除緩沖。不過(guò)貌似雨中飛燕大姐說(shuō)這個(gè)用法是非標(biāo)準(zhǔn)的。K&R,只是說(shuō)行為沒(méi)有定義,但我們可以使用while((c=getchar())!='\n'&&c!=EOF);同樣可以清除后面的垃圾scanf的格式匹配還是比較簡(jiǎn)單,一定要記住的就是普通變量一定要加上&,否則編譯器無(wú)法檢測(cè)錯(cuò)誤,但運(yùn)行肯定會(huì)段錯(cuò)誤。
代碼及意義
%a讀浮點(diǎn)值(僅適用于 C99)
%A讀浮點(diǎn)值(僅適用于 C99)
%c 讀單字符
%d 讀十進(jìn)制整數(shù)
%i 讀十進(jìn)制、八進(jìn)制、十六進(jìn)制整數(shù)
%e 讀浮點(diǎn)數(shù)
%E 讀浮點(diǎn)數(shù)
%f 讀浮點(diǎn)數(shù)
%F 讀浮點(diǎn)數(shù)(僅適用于 C99)
%g 讀浮點(diǎn)數(shù)
%G 讀浮點(diǎn)數(shù)
%o 讀八進(jìn)制數(shù)
%s 讀字符串
%x 讀十六進(jìn)制數(shù)
%X 讀十六進(jìn)制數(shù)
%p 讀指針值
%n 至此已讀入值的等價(jià)字符數(shù)
%u 讀無(wú)符號(hào)十進(jìn)制整數(shù)
%[ ] 掃描字符集合
%%讀 % 符號(hào)(百分號(hào))
前面都很簡(jiǎn)單,%p,%n很少用到,跳過(guò)。要輸入%必須要在前面再加一個(gè)%,重點(diǎn)來(lái)談?wù)?s和%[]。%s是讀入一個(gè)數(shù)組,他與gets的區(qū)別就在于%s會(huì)以任何的空字符結(jié)束,而gets是回車(chē)結(jié)束。同樣%s前可以加數(shù)字,表示只讀多少個(gè)。ANSI C 標(biāo)準(zhǔn)向 scanf() 增加了一種新特性,稱(chēng)為掃描集(scanset)。 掃描集定義一個(gè)字符集合,可由 scanf() 讀入其中允許的字符并賦給對(duì)應(yīng)字符數(shù)組。 掃描集合由一對(duì)方括號(hào)中的一串字符定義,左方括號(hào)前必須綴以百分號(hào)。 例如,以下的掃描集使 scanf() 讀入字符 A、B 和 C:
%[ABC]
使用掃描集時(shí),scanf() 連續(xù)吃進(jìn)集合中的字符并放入對(duì)應(yīng)的字符數(shù)組,直到發(fā)現(xiàn)不在集合中的字符為止(即掃描集僅讀匹配的字符)。返回時(shí),數(shù)組中放置以 null 結(jié)尾、由讀入字符組成的字符串。對(duì)于許多實(shí)現(xiàn)來(lái)說(shuō),用連字符可以說(shuō)明一個(gè)范圍。 例如,以下掃描集使 scanf() 接受字母 A 到 Z:
%[A-Z]
重要的是要注意掃描集是區(qū)分大小寫(xiě)的。因此,希望掃描大、小寫(xiě)字符時(shí),應(yīng)該分別說(shuō)明大、小寫(xiě)字母。對(duì)于%[]還可以用^+任意字符(包括eof)來(lái)結(jié)束字符串的輸入。比如%[^EOF]就是直到有EOF輸入,字符串才中止。但一定要記住就是c語(yǔ)言是緩沖輸入,即使你%[^a],再你輸入回車(chē)之前輸入多少的a都是不可能結(jié)束的。%s的輸入會(huì)跳過(guò)空白字符,但是%c則不會(huì)。這也就是
scanf("%d", &h);
scanf("%c", &c);
如果這寫(xiě)的話,變量c放的一定是回車(chē)。如果想實(shí)現(xiàn)這種輸入,可以在兩個(gè)語(yǔ)句之間加入一個(gè)getchar(),他可以吃掉這個(gè)回車(chē),也可用scanf("%d %c",&h,&c);來(lái)做,再輸入數(shù)字后加一個(gè)空格。就可以了但千萬(wàn)別用scanf("%d\n", &h); K&R說(shuō)的十分清楚,任何非格式化的字符都需要完全匹配。意味著,只有輸入數(shù)字后面再加\n才是合法的。還有就是*加在任何項(xiàng)的前面表示該項(xiàng)不符值。