iostream與iostream.h的區(qū)別詳細(xì)解析
C++的標(biāo)準(zhǔn)類庫(kù)被修訂了兩次,有兩個(gè)標(biāo)準(zhǔn) C92和C99,這兩個(gè)庫(kù)現(xiàn)在都在并行使用,用 .h 包含的是c92 ,不帶 .h 的是c99的頭文件,對(duì)于普通用戶來(lái)說(shuō)這兩者沒(méi)有什么區(qū)別,區(qū)別是在內(nèi)部函數(shù)的具體實(shí)現(xiàn)上。舊的C++頭文件是官方明確反對(duì)使用的,但舊的C頭文件則沒(méi)有(以保持對(duì)C的兼容性)。據(jù)說(shuō)從 Visual C++ .NET 2003 開(kāi)始,移除了舊的 iostream 庫(kù)。其實(shí)編譯器制造商不會(huì)停止對(duì)客戶現(xiàn)有軟件提供支持,所以在可以預(yù)計(jì)的將來(lái),舊的C++頭文件還會(huì)囂張一段時(shí)間。如果能明白字符串頭文件的使用,舉一反三,其他的也差不多會(huì)用了:
<string.h>是舊的C/C++頭文件,對(duì)應(yīng)的是基于char*的字符串處理函數(shù);
<string>是包裝了std的C++頭文件,對(duì)應(yīng)的是新的strng類;
<cstring>是對(duì)應(yīng)舊的C頭文件的std版本。
如果編譯器都同時(shí)支持< iostream >和< iostream.h >,那使用#include < iostream >,得到的是置于名字空間std下的iostream庫(kù)的元素;如果使用#include < iostream.h >,得到的是置于全局空間的同樣的元素。在全局空間獲取元素會(huì)導(dǎo)致名字沖突,而設(shè)計(jì)名字空間的初衷正是用來(lái)避免這種名字沖突的發(fā)生。
想象訊雷下載軟件一樣,先從服務(wù)器確定下載文件的大小,初始時(shí)即保存文件,全部填充0,多個(gè)線程下載數(shù)據(jù)直接寫入文件,對(duì)自己線程負(fù)責(zé)下載的那段文件片的0進(jìn)行改寫,其中就涉及到文件共享寫的操作
出現(xiàn)的問(wèn)題時(shí):
vc7.1<fstream> 已經(jīng)不支持 filebuf::sh_read等關(guān)鍵字,不知在vc7下若要用文件流來(lái)對(duì)文件進(jìn)行非獨(dú)占讀和寫操作該如何實(shí)現(xiàn)?
而:
vc6.0中的iostream.h <fstream.h>
filebuf::sh_read
filebuf::sh_write
filebuf::sh_note
filebuf::sh_openprot
無(wú)論自己是用vc6或者vc7的IDE
當(dāng)用到標(biāo)準(zhǔn)的輸入輸出和文件流時(shí)都是:
include<iostream>
include<fstream>
using namespace std;
有兩種用法:
A:
include<iostream.h>
include<fstream.h>
B:
include<iostream>
include<fstream>
A是標(biāo)準(zhǔn)用法,B是老式用法。
如果用了<iostream>,則一定要引入命名空間,即"using namespace std;".
如果用了<iostream.h>,則不那引入命名空間,否則會(huì)引起編譯錯(cuò)誤,提示找不到命名空間,例程如下:
//情況一:使用<iostream>和命名空間
#include <iostream>
using namespace std;
int main()
{
cout<<"<iostream> need to use namespace std!/n";
return 0;
}
輸出:
<iostream> need to use namespace std!
Press any key to continue
//情況二:使用<iostream.h>,不引入命名空間
#include <iostream.h>
//using namespace std;
int main()
{
cout<<"<iostream> need to use namespace std!/n";
return 0;
}
輸出:
<iostream> need to use namespace std!
Press any key to continue
//情況三:使用<iostream.h>,引入命名空間,這時(shí)候編譯出錯(cuò)
#include <iostream.h>
using namespace std;
int main()
{
cout<<"<iostream> need to use namespace std!/n";
return 0;
}
編譯錯(cuò)誤信息:
error C2871: 'std' : does not exist or is not a namespace
從 Visual C++ .NET 2003 開(kāi)始,移除了舊的 iostream 庫(kù)。
標(biāo)準(zhǔn) C++ 庫(kù)和以前的運(yùn)行時(shí)庫(kù)之間的主要差異在于 iostream 庫(kù)。iostream 實(shí)現(xiàn)的具體細(xì)節(jié)已經(jīng)更改,如果想鏈接標(biāo)準(zhǔn) C++ 庫(kù),可能有必要重寫代碼中使用 iostream 的部分。
必須移除任何包含在代碼中的舊 iostream 頭文件(fstream.h、iomanip.h、ios.h、iostream.h、istream.h、ostream.h、streamb.h 和 strstrea.h),并添加一個(gè)或多個(gè)新的標(biāo)準(zhǔn) C++ iostream 頭文件(<fstream>、<iomanip>、<ios>、<iosfwd>、<iostream>、<istream>、<ostream>、<sstream>、<streambuf> 和 <strstream>,所有頭文件都沒(méi)有 .h 擴(kuò)展名)。
下表描述新的標(biāo)準(zhǔn) C++ iostream 庫(kù)不同于舊 iostream 庫(kù)的行為。
在新的標(biāo)準(zhǔn) C++ iostream 庫(kù)中:
open 函數(shù)不采用第三個(gè)參數(shù)(保護(hù)參數(shù))。
無(wú)法從文件句柄創(chuàng)建流。
除了幾個(gè)例外,新的標(biāo)準(zhǔn) C++ 庫(kù)中的所有名稱都在 std 命名空間中。有關(guān)更多信息,請(qǐng)參見(jiàn)使用 C++ 庫(kù)頭。
單獨(dú)用 ios::out 標(biāo)志無(wú)法打開(kāi) ofstream 對(duì)象。ios::out 標(biāo)志必須在邏輯 OR 中和另一個(gè) ios 枚舉數(shù)組合;比如,和 ios::in 或 ios::app 組合。
因?yàn)樵O(shè)置了 eofbit 狀態(tài),到達(dá)文件尾后 ios::good 不再返回非零值。
除非知道當(dāng)前沒(méi)有設(shè)置基標(biāo)志,否則 ios::setf(_IFlags) 不應(yīng)和 ios::dec、ios::oct 或 ios::hex 的標(biāo)志值一起使用。格式化的輸入/輸出函數(shù)和運(yùn)算符假定只設(shè)置了一個(gè)基。改用 ios_base。例如,setf( ios_base::oct, ios_base::basefield ) 清除所有基信息并將基設(shè)置成八進(jìn)制。
ios::unsetf 返回 void 而不是以前的值。
若出現(xiàn)錯(cuò)誤,istream::get( char& _Rch ) 不分配給 Rch。
istream::get( char* _Pch, int _Ncount, char _Delim ) 有三點(diǎn)不同:
沒(méi)讀取任何內(nèi)容時(shí)設(shè)置 failbit。
提取的字符后總是存儲(chǔ)一個(gè) eos(與結(jié)果無(wú)關(guān))。
值為 -1 時(shí) _Ncount 是一個(gè)錯(cuò)誤。
具有無(wú)效參數(shù)的 istream::seekg 不設(shè)置 failbit。
返回類型 streampos 是具有重載運(yùn)算符的類。在返回 streampos 值(比如 istream::tellg、ostream::tellp、strstreambuf::seekoff 和 strstreambuf::seekpos)的函數(shù)中,應(yīng)將返回值轉(zhuǎn)換成所需的類型:streamoff、fpos_t 或 mbstate_t。
strstreambuf::strstreambuf( _Falloc, _Ffree ) 中的第一個(gè)函數(shù)參數(shù)采用 size_t 參數(shù)而不是 long。
除了上述改動(dòng)外,以下作為舊 iostream 庫(kù)元素的函數(shù)、常數(shù)和枚舉數(shù)不是新 iostream 庫(kù)的元素:
filebuf、fstream ifstream 和 ofstream 的 attach 成員函數(shù)
filebuf、fstream ifstream 和 ofstream 的 fd 成員函數(shù)
filebuf::openprot
filebuf::setmode
ios::bitalloc
ios::nocreate
ios::noreplace
ios::sync_with_stdio
streambuf::out_waiting
streambuf::setbuf(相同的行為使用 rdbuf -> pubsetbuf)
STL FAQ 上有對(duì)標(biāo)準(zhǔn)庫(kù)用法的一些建議,在《軟件研發(fā)》雜志上也有這方面的討論的文章,可惜,這么好的雜志也??耍赡苌厦娴闹R(shí)對(duì)中國(guó)的程序員太過(guò)超前了,別人說(shuō)的,奇怪,我怎么看得明白了).
What's the difference between <xxx> and <xxx.h> headers
The headers in ISO Standard C++ don't have a .h suffix. This is something the standards committee changed from former practice. The details are different between headers that existed in C and those that are specific to C++.
The C++ standard library is guaranteed to have 18 standard headers from the C language. These headers come in two standard flavors, <cxxx> and <xxx.h> (where xxx is the basename of the header, such as stdio, stdlib, etc). These two flavors are identical except the <cxxx> versions provide their declarations in the std namespace only, and the<xxx.h> versions make them available both in std namespace and in the global namespace. The committee did it this way so that existing C code could continue to be compiled in C++. However the <xxx.h> versions are deprecated, meaning they are standard now but might not be part of the standard in future revisions. (See clause D.5 of the ISO C++ standard.)
The C++ standard library is also guaranteed to have 32 additional standard headers that have no direct counterparts in C, such as <iostream>, <string>, and <new>. You may see things like #include <iostream.h> and so on in old code, and some compiler vendors offer .h versions for that reason. But be careful: the .h versions, if available, may differ from the standard versions. And if you compile some units of a program with, for example, <iostream> and others with <iostream.h>, the program may not work.
For new projects, use only the<xxx> headers, not the<xxx.h> headers.
When modifying or extending existing code that uses the old header names, you should probably follow the practice in that code unless there's some important reason to switch to the standard headers (such as a facility available in standard<iostream> that was not available in the vendor's <iostream.h>). If you need to standardize existing code, make sure to change all C++ headers in all program units including external libraries that get linked in to the final executable.
All of this affects the standard headers only. You're free to name your own headers anything you like; see [27.9].
標(biāo)準(zhǔn)庫(kù)擴(kuò)展了原庫(kù),例如新庫(kù)<string>還支持寬字符集的操作,所以我認(rèn)為在現(xiàn)在大多數(shù)的編譯器都已支持標(biāo)準(zhǔn)C++的情況下,所有的程序都應(yīng)該使用標(biāo)準(zhǔn)頭文件的導(dǎo)入方式!
對(duì)于名字空間 namespace std 的使用,C++ 的 FAQ 的回答是這樣的
Should I use using namespace std in my code?
Probably not.
People don't like typing std:: over and over, and they discover that using namespace std lets the compiler see any std name, even if unqualified. The fly in that ointment is that it lets the compiler see any std name, even the ones you didn't think about. In other words, it can create name conflicts and ambiguities.
For example, suppose your code is counting things and you happen to use a variable or function named count. But the std library also uses the name count (it's one of the std algorithms), which could cause ambiguities.
Look, the whole point of namespaces is to prevent namespace collisions between two independently developed piles of code. The using-directive (that's the technical name for using namespace XYZ) effectively dumps one namespace into another, which can subvert that goal. The using-directive exists for legacy C++ code and to ease the transition to namespaces, but you probably shouldn't use it on a regular basis, at least not in your new C++ code.
If you really want to avoid typing std::, then you can either use something else called a using-declaration, or get over it and just type std:: (the un-solution):
Use a using-declaration, which brings in specific, selected names. For example, to allow your code to use the name cout without a std:: qualifier, you could insert using std::cout into your code. This is unlikely to cause confusion or ambiguity because the names you bring in are explicit.
just type std:: (the un-solution):
#include <vector>
#include <iostream>
void f(const std::vector<double>& v)
{
using std::cout;// ← a using-declaration that lets you use cout without qualification
cout << "Values:";
for (std::vector<double>::const_iterator p = v.begin(); p != v.end(); ++p)
cout << ' ' << *p;
cout << '/n';
}
Get over it and
#include <vector>
#include <iostream>
void f(const std::vector<double>& v)
{
std::cout << "Values:";
for (std::vector<double>::const_iterator p = v.begin(); p != v.end(); ++p)
std::cout << ' ' << *p;
std::cout << '/n';
}
I personally find it's faster to type "std::" than to decide, for each distinct std name, whether
or not to include a using-declaration and if so, to find the best scope and add it there. But
either way is fine. Just remember that you are part of a team, so make sure you use an approach
that is consistent with the rest of your organization.
欄 目:C語(yǔ)言
本文標(biāo)題:iostream與iostream.h的區(qū)別詳細(xì)解析
本文地址:http://mengdiqiu.com.cn/a1/Cyuyan/4126.html
您可能感興趣的文章
- 01-10全排列算法的非遞歸實(shí)現(xiàn)與遞歸實(shí)現(xiàn)的方法(C++)
- 01-10深入理解atoi()與itoa()函數(shù)的用法
- 01-10淺談C/C++中的static與extern關(guān)鍵字的使用詳解
- 01-10基于atoi()與itoa()函數(shù)的內(nèi)部實(shí)現(xiàn)方法詳解
- 01-10Linux線程管理必備:解析互斥量與條件變量的詳解
- 01-10深入理解大數(shù)與高精度數(shù)的處理問(wèn)題
- 01-10深入理解數(shù)組指針與指針數(shù)組的區(qū)別
- 01-10C語(yǔ)言游戲必備:光標(biāo)定位與顏色設(shè)置的實(shí)現(xiàn)方法
- 01-10深入探討C語(yǔ)言中局部變量與全局變量在內(nèi)存中的存放位置
- 01-10linux c 查找使用庫(kù)的cflags與libs的方法詳解


閱讀排行
- 1C語(yǔ)言 while語(yǔ)句的用法詳解
- 2java 實(shí)現(xiàn)簡(jiǎn)單圣誕樹(shù)的示例代碼(圣誕
- 3利用C語(yǔ)言實(shí)現(xiàn)“百馬百擔(dān)”問(wèn)題方法
- 4C語(yǔ)言中計(jì)算正弦的相關(guān)函數(shù)總結(jié)
- 5c語(yǔ)言計(jì)算三角形面積代碼
- 6什么是 WSH(腳本宿主)的詳細(xì)解釋
- 7C++ 中隨機(jī)函數(shù)random函數(shù)的使用方法
- 8正則表達(dá)式匹配各種特殊字符
- 9C語(yǔ)言十進(jìn)制轉(zhuǎn)二進(jìn)制代碼實(shí)例
- 10C語(yǔ)言查找數(shù)組里數(shù)字重復(fù)次數(shù)的方法
本欄相關(guān)
- 04-02c語(yǔ)言函數(shù)調(diào)用后清空內(nèi)存 c語(yǔ)言調(diào)用
- 04-02func函數(shù)+在C語(yǔ)言 func函數(shù)在c語(yǔ)言中
- 04-02c語(yǔ)言的正則匹配函數(shù) c語(yǔ)言正則表達(dá)
- 04-02c語(yǔ)言用函數(shù)寫分段 用c語(yǔ)言表示分段
- 04-02c語(yǔ)言中對(duì)數(shù)函數(shù)的表達(dá)式 c語(yǔ)言中對(duì)
- 04-02c語(yǔ)言編寫函數(shù)冒泡排序 c語(yǔ)言冒泡排
- 04-02c語(yǔ)言沒(méi)有round函數(shù) round c語(yǔ)言
- 04-02c語(yǔ)言分段函數(shù)怎么求 用c語(yǔ)言求分段
- 04-02C語(yǔ)言中怎么打出三角函數(shù) c語(yǔ)言中怎
- 04-02c語(yǔ)言調(diào)用函數(shù)求fibo C語(yǔ)言調(diào)用函數(shù)求
隨機(jī)閱讀
- 08-05DEDE織夢(mèng)data目錄下的sessions文件夾有什
- 01-11ajax實(shí)現(xiàn)頁(yè)面的局部加載
- 01-10使用C語(yǔ)言求解撲克牌的順子及n個(gè)骰子
- 01-10delphi制作wav文件的方法
- 01-10SublimeText編譯C開(kāi)發(fā)環(huán)境設(shè)置
- 01-11Mac OSX 打開(kāi)原生自帶讀寫NTFS功能(圖文
- 04-02jquery與jsp,用jquery
- 08-05dedecms(織夢(mèng))副欄目數(shù)量限制代碼修改
- 08-05織夢(mèng)dedecms什么時(shí)候用欄目交叉功能?
- 01-10C#中split用法實(shí)例總結(jié)