- 1、本文档共3页,可阅读全部内容。
- 2、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
- 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
getchar返回值
许多初学者都习惯用 char 型变量接收 getchar、getc,fgetc 等函数的返回值,其实这么做是不对的,并且隐含着足以致命的错误。
getchar 等函数的返回值类型都是 int 型,当这些函数读取出错或者读完文件后,会返回 EOF。EOF 是一个宏,标准规定它的值必须是一个 int 型的负数常量。通常编译器都会把 EOF 定义为 -1。
问题就出在这里,使用 char 型变量接收 getchar 等函数的返回值会导致对 EOF 的辨认出错,或者错把好的数据误认为是 EOF,或者把 EOF 误认为是好的数据。
例如: int c; /* 正确。应该使用 int 型变量接收 fgetc 的返回值 */
while ( (c = fgetc(fp)) != EOF )
?{
?putchar(c);
}
如上例所示,我们很多时候都需要先用一个变量接收 fgetc 等函数的返回值,然后再用这个变量和 EOF 比较,判断是否已经读完文件。上面这个例子是正确的,把 c 定义为 int 型保证了它能正确接收 fgetc 返回的 EOF,从而保证了这个比较的正确性。
但是,如果把 c 定义为 char 型,则会导致意想不到的后果。
首先,因为 fgetc 等函数的返回值是 int 型的,当赋值给 char 型变量时,会发生降级,从而导致数据截断。
例如: | 十进制 | int | char |
?| 10 | 00 00 00 0A | 0A |
| -1 | FF FF FF FF | FF |
?| -2 | FF FF FF FE | FE |
在此,我们假设 int 和 char 分别是 32 位和 8 位的。由上表可得,从 int 型到 char 型,损失了 3 个字节的数据。而当我们要拿 char 型和 int 型比较的时候,char 型会自动升级为 int 型。char 型升级为 int 型后的值会因为它到底是 signed char 还是 unsigned char 而有所不同。不幸的是,如果我们没有使用 signed 或者 unsigned 来修饰 char,那么我们无从知晓 char 到底是指 unsigned char 还是指 signed char,因为这是由编译器决定的。不过,无论 char 是 signed 的也好,unsigned 的也罢,都不能改变使用 char 型变量接收 fgetc 等函数的返回值是错误的这个事实。唯一能改变的是该错误导致的后果。前面我们说了,char 型和 int 型比较时,char 会自动升级为 int,下面我们来看看 signed char 和 unsigned char 在转换成 int 后,它们的值有什么不同:--------------------------------------- | char | unsigned | signed ||-------|---------------|-------------|
| 10 | 00 00 00 0A | 00 00 00 0A | | FF | 00 00 00 FF | FF FF FF FF | | FE | 00 0000 FE | FF FF FF FE | ---------------------------------------由上表可知,当 char 是 unsigned 的时候,其转换为 int 后的值是正数。也就是说,假如我们把 c 定义为 char 型变量,而编译器默认 char 为 unsigned char,那么以下表达式将永远成立。 (c = fgetc(fp)) != EOF /* c 的值永远为正数,而标准规定 EOF 为负数 */ 也就是说以下循环是一个死循环。 while ( (c = fgetc(fp)) !=EOF ) { putchar(c); } 读到这里,可能有些读者朋友会说:“那么我明确把 c 定义为 signed char 型的就没问题了吧!”很遗憾,就算把 c 定义为 signed char,仍然是错误的。假设 fgetc 等函数读到一个字节的值为 FF,那么返回值就是 00 00 00 FF。把这个值赋值给 c 后, c 的值变成 FF。然后 c 的值为了和 EOF 比较,会自动升级为 int 型的值,也就是 FF FF FF FF。从而导致以下表达式不成立。 (c = fgetc(fp)) != EOF /* 读到值为 FF 的字符,误认为 EOF */ 也就是说以下循环在没有读完文件的情况下提前退出。 while ( (c = fgetc(fp)) !=EOF ) { putchar(c); } 综上所述,使用 char 型变量接收 f
您可能关注的文档
最近下载
- 专利代理实务考前必背模板.doc VIP
- ГОСТ 17375-2001- 俄标弯头中文版.pdf
- 小学音乐教师业务考试试卷一(含答案).pdf VIP
- 建设单位设置业主代表的重要性一 - 莆田市交通投资集团有限公司.ppt
- 2024年国家开放大学《护理伦理学》形考(带答案).pdf VIP
- 国家科学技术进步奖提名书-中国发明协会.PDF
- 2024年国家开放大学(电大)-广告学(本科)笔试历年真题荟萃含答案.docx
- 广东省珠海市金湾区2022-2023学年四年级上学期期末语文试卷.docx VIP
- 小电流接地系统单相接地故障选线装置的设计本科学位论文.doc
- (2021更新)国家开放大学电大本科《企业信息管理》2021期末试题及答案(1055套).pdf
文档评论(0)