QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 4901|回复: 0
打印 上一主题 下一主题

borland c++ bulder的文件操作总结-1

[复制链接]
字体大小: 正常 放大
韩冰        

823

主题

3

听众

4048

积分

我的地盘我做主

该用户从未签到

发帖功臣 元老勋章

跳转到指定楼层
1#
发表于 2005-1-26 13:07 |只看该作者 |倒序浏览
|招呼Ta 关注Ta
<>、基于C的文件操作
: g5 ^7 h8 t( A- ]0 r% W  在ANSI C中,对文件的操作分为两种方式,即流式文件操作和I/O文件操作,下面就分别介绍之。</P>
$ g3 w8 e; ?5 B& I: B- h2 N<>一、流式文件操作, p  i) l  [) y' p
  这种方式的文件操作有一个重要的结构FILE,FILE在stdio.h中定义如下:</P>. {# K- Y- q) V5 R2 o& ?
<>typedef struct {
7 Q0 ?3 x( k4 K  I9 sint level; /* fill/empty level of buffer */: T; k& H% ]; }7 N+ s! e
unsigned flags; /* File status flags */: B5 D: N& K$ J" q+ Q
char fd; /* File descriptor */
. T) J9 u( {$ W* O  H  d9 J% Junsigned char hold; /* Ungetc char if no buffer */) G. i8 U5 K; r; [* ?6 G, [' ^
int bsize; /* Buffer size */+ [: A$ X% I% k1 C' G8 Y
unsigned char _FAR *buffer; /* Data transfer buffer */
$ _. T5 C" e- Q9 z3 yunsigned char _FAR *curp; /* Current active pointer */
6 P5 I! F* z- s- w6 gunsigned istemp; /* Temporary file indicator */# O# |4 e8 m3 _( q8 H" f4 D
short token; /* Used for validity checking */0 I8 S! K# ?. Q% K5 W
} FILE; /* This is the FILE object */</P>. O, U' x# h  q
<>  FILE这个结构包含了文件操作的基本属性,对文件的操作都要通过这个结构的指针来进行,此种文件操作常用的函数见下表 函数 功能
5 E2 ?" a2 d( J3 [  |# I" qfopen() 打开流 3 a; s% R4 e/ }  ], O4 `& q- I
fclose() 关闭流 8 P& P1 R1 ^; `: e. g/ ~- ?8 P
fputc() 写一个字符到流中 . l6 r0 J( D* B1 N. F& _1 G0 I
fgetc() 从流中读一个字符
1 m/ F) p" _  efseek() 在流中定位到指定的字符
' V- Q! k9 x$ r0 L* v/ Kfputs() 写字符串到流 & U$ u( A" i& F& \: r
fgets() 从流中读一行或指定个字符 9 d2 r2 |. M1 u& B  P; N
fprintf() 按格式输出到流 . h; Q/ [  l/ ?
fscanf() 从流中按格式读取
' w$ X& ]/ d& P6 J+ D4 ^feof() 到达文件尾时返回真值 7 Z4 C9 q- [" w4 }6 M% c0 {
ferror() 发生错误时返回其值
& r2 o! @: u) Q  E9 L: y9 J+ z, Urewind() 复位文件定位器到文件开始处
; ]( I9 w, e7 d8 U  f$ p/ kremove() 删除文件 & ^. v" A. i  r
fread() 从流中读指定个数的字符 - N2 a+ c8 F" d: ?8 k  ]
fwrite() 向流中写指定个数的字符
" B: v: G; J$ p: J6 ptmpfile() 生成一个临时文件流
. @! }& z# l# e4 w  y' V2 u" r) v; itmpnam() 生成一个唯一的文件名 </P>
8 s' k' z/ L) C$ ?<>
* M( O6 t' h) U) i# {2 M6 |" C  下面就介绍一下这些函数</P>! B$ ~- ]# M& I. X- w
<>1.fopen()
9 I/ X7 Z; ?. A3 F' p  fopen的原型是:FILE *fopen(const char *filename,const char *mode),fopen实现三个功能</P>
3 f+ Q# P3 Q8 O4 V2 s<>为使用而打开一个流
# |! m- [$ z8 G; X3 S( D把一个文件和此流相连接 - P5 }* o' N3 X. f
给此流返回一个FILR指针4 D+ \: \, {, R; J1 u- }
参数filename指向要打开的文件名,mode表示打开状态的字符串,其取值如下表</P>
0 B# D0 v9 `! S<>字符串 含义 6 B- `% |% d; L, d
"r" 以只读方式打开文件 ; s5 X  W9 B# S' i- c  M: X6 |% S
"w" 以只写方式打开文件 : s3 r9 `: |7 q: \4 G0 r: P/ n
"a" 以追加方式打开文件 / o2 B) l" }7 H
"r+" 以读/写方式打开文件,如无文件出错 0 g! ]8 o. ~5 c5 V+ `: @
"w+" 以读/写方式打开文件,如无文件生成新文件 </P>
8 _  W7 ~- b" x8 H9 P<>  一个文件可以以文本模式或二进制模式打开,这两种的区别是:在文本模式中回车被当成一个字符'\n',而二进制模式认为它是两个字符0x0D,0x0A;如果在文件中读到0x1B,文本模式会认为这是文件结束符,也就是二进制模型不会对文件进行处理,而文本方式会按一定的方式对数据作相应的转换。</P>
0 b3 R3 O9 b! ~' O4 w<>  系统默认的是以文本模式打开,可以修改全部变量_fmode的值来修改这个设置,例如_fmode=O_TEXT;就设置默认打开方式为文本模式;而_fmode=O_BINARY;则设置默认打开方式是二进制模式。</P>
: n, ~# B. l! i+ w# Y9 a* @; |<>  我们也可以在模式字符串中指定打开的模式,如"rb"表示以二进制模式打开只读文件,"w+t"或"wt+"表示以文本模式打开读/写文件。</P>
( O  n9 [) S8 W) [<>  此函数返回一个FILE指针,所以申明一个FILE指针后不用初始化,而是用fopen()来返回一个指针并与一个特定的文件相连,如果成败,返回NULL。</P>, N: p0 r* d# O, `' Y) @
<>例:</P>
3 ~. q" l) s2 \0 P; @<>  FILE *fp;
2 {! z" h# ]3 v# }+ k' w  if(fp=fopen("123.456","wb"))0 I; @  w: v* N
    puts("打开文件成功");
, e5 w/ L1 ?' K  else " ], K5 s# T  [* N
    puts("打开文件成败"); </P>
! }- l& M+ J7 m9 o6 x<>2.fclose() $ Z) U3 ~/ C3 b7 n- s
  fclose()的功能就是关闭用fopen()打开的文件,其原型是:int fclose(FILE *fp);如果成功,返回0,失败返回EOF。</P>
$ W4 E, x. X) J- ]<>  在程序结束时一定要记得关闭打开的文件,不然可能会造成数据丢失的情况,我以前就经常犯这样的毛病。</P>
/ b. ]! m' A" [! w& X# b4 t* p<>例:fclose(fp);</P>$ g1 G  O/ V; ]# |
<>3.fputc()' x  y4 X# n( d, m, j4 e' W' I# l9 M9 m
  向流写一个字符,原型是int fputc(int c, FILE *stream); 成功返回这个字符,失败返回EOF。</P>
" E: j1 ]/ s! T8 P7 q5 w<>例:fputc('X',fp);</P>
7 \+ `; K! n, t7 ]<>4.fgetc()$ q8 I- h% F& V. [& w- J1 i
  从流中读一个字符,原型是int fputc(FILE *stream); 成功返回这个字符,失败返回EOF。</P>$ P5 ~' \/ P4 i" n# s) }
<>例:char ch1=fgetc(fp);</P>
: ?6 m" n3 ?6 ]: O8 Z0 a( [<>5. fseek()% u- A7 }  ]/ l3 X5 I
  此函数一般用于二进制模式打开的文件中,功能是定位到流中指定的位置,原型是int fseek(FILE *stream, long offset, int whence);如果成功返回0,参数offset是移动的字符数,whence是移动的基准,取值是</P>
! \9 ]) f( }6 q% i0 Z! a<>符号常量 值 基准位置 2 _8 m$ x: F. q
SEEK_SET 0 文件开头
' G4 D; |4 n0 m0 R0 u8 bSEEK_CUR 1 当前读写的位置
6 Q, d/ `1 ?4 r$ d' ?! rSEEK_END 2 文件尾部 </P>
1 ~2 u6 [% }" i8 d* Q, S& g/ l<>例:fseek(fp,1234L,SEEK_CUR);//把读写位置从当前位置向后移动1234字节(L后缀表示长整数)</P>
( g7 r/ c/ Y6 Q2 z: d<>  fseek(fp,0L,2);//把读写位置移动到文件尾</P>! r+ B1 z9 u, g
<>6.fputs()+ N: W# T1 u) X1 r
  写一个字符串到流中,原型int fputs(const char *s, FILE *stream); </P>9 F6 U+ q+ ]0 h" T
<>例:fputs("I Love You",fp);</P>$ `) x$ M( F4 Y
<>7.fgets()" R/ }+ |* n2 o' x+ b' P4 q. [
  从流中读一行或指定个字符,原型是char *fgets(char *s, int n, FILE *stream); 从流中读取n-1个字符,除非读完一行,参数s是来接收字符串,如果成功则返回s的指针,否则返回NULL。</P>
6 X6 B2 Z% o9 u- s+ U<>例:如果一个文件的当前位置的文本如下</P>7 z, M7 U$ r% H6 x- @5 f5 ~
<>Love ,I Have</P>
8 c" `8 C8 T" F: R! {& b<P>But ........</P>
$ v/ E! i! o/ c<P>如果用</P>
% m# M% y: L( I- ?$ f% Q<P>  fgets(str1,4,file1);</P>. {! }1 g# d0 w! p
<P>则执行后str1="Lov",读取了4-1=3个字符,而如果用</P>
3 u" p0 y. k: f6 `<P>  fgets(str1,23,file1);</P># k- ^( B8 _0 n, {0 [' L
<P>则执行str="Love ,I Have",读取了一行(不包括行尾的'\n')。</P>
2 T4 J! h  l. i0 R. w<P>8.fprintf()) S# f' S' N- F: k  n8 `, T9 _
  按格式输入到流,其原型是int fprintf(FILE *stream, const char *format[, argument, ...]);其用法和printf()相同,不过不是写到控制台,而是写到流罢了</P>
3 Y8 }# T! V+ ?4 t<P>例:fprintf(fp,"%2d%s",4,"Hahaha");</P>
1 z4 x! f  F, {7 w2 ]2 k0 @6 A<P>9.fscanf()
) V2 K, g% G0 P; I$ O0 H  从流中按格式读取,其原型是int fscanf(FILE *stream, const char *format[, address, ...]);其用法和scanf()相同,不过不是从控制台读取,而是从流读取罢了。</P>9 F- a, e$ e- s# o9 f4 Z9 ?
<P>例:fscanf(fp,"%d%d" ,&amp;x,&amp;y);</P>
5 K4 o  p+ G& y6 |8 @<P>10.feof()% R8 V/ c) {  V& ?0 m" h
  检测是否已到文件尾,是返回真,否则返回0,其原型是int feof(FILE *stream);</P>7 i5 L1 s( f2 R6 K
<P>例:if(feof(fp))printf("已到文件尾");</P>
, I4 B% c  B, b& y. r/ s' |- b7 i<P>11.ferror()
. F  _  ]0 m% ^3 o  }  原型是int ferror(FILE *stream);返回流最近的错误代码,可用clearerr()来清除它,clearerr()的原型是void clearerr(FILE *stream);</P>9 @: B+ \9 R" W3 f- X, G% x3 J
<P>例:printf("%d",ferror(fp));</P>: j$ C) E2 W! I7 p( R+ V
<P>12.rewind()
, C$ V+ D: a  d2 R5 Q8 G( D  把当前的读写位置回到文件开始,原型是void rewind(FILE *stream);其实本函数相当于fseek(fp,0L,SEEK_SET);</P>8 Z, o+ m& x& v" a5 |0 D
<P>例:rewind(fp);</P>+ t" \8 Z6 k% S! }% F& j, o
<P>12.remove()
: ]- ?9 S/ B- T# r  b  删除文件,原型是int remove(const char *filename); 参数就是要删除的文件名,成功返回0。</P>6 y6 |! P( T. k8 r+ c  F' c
<P>例:remove("c:\\io.sys");</P>& S( b$ m; a0 n! |
<P>13.fread()
8 a6 U; @/ W# S: _# e; v- e$ Z  从流中读指定个数的字符,原型是size_t fread(void *ptr, size_t size, size_t n, FILE *stream);参数ptr是保存读取的数据,void*的指针可用任何类型的指针来替换,如char*、int *等等来替换;size是每块的字节数;n是读取的块数,如果成功,返回实际读取的块数(不是字节数),本函数一般用于二进制模式打开的文件中。</P>
- N  r: R' c/ ?8 [<P>例:</P>
/ i5 Z2 I' I7 i" y. I. K<P>  char x[4230];
$ `1 T2 J2 I4 r" e$ c# ^  FILE *file1=fopen("c:\\msdos.sys","r");8 `2 [3 r! `0 A/ z
  fread(x,200,12 ,file1);//共读取200*12=2400个字节</P>
* m6 D# _$ W) h' J<P>14.fwrite()
9 j9 C& g: V5 g# u6 o  与fread对应,向流中写指定的数据,原型是size_t fwrite(const void *ptr, size_t size, size_t n, FILE *stream);参数ptr是要写入的数据指针,void*的指针可用任何类型的指针来替换,如char*、int *等等来替换;size是每块的字节数;n是要写的块数,如果成功,返回实际写入的块数(不是字节数),本函数一般用于二进制模式打开的文件中。</P>/ |' T. p9 q( E7 [$ s
<P>例:</P>' [  y4 \2 V) c; Z( q
<P>  char x[]="I Love You";1 ?. ?' b$ Q' v
  fwire(x, 6,12,fp);//写入6*12=72字节</P>7 {- L- Y- F8 e
<P>  将把"I Love"写到流fp中12次,共72字节</P>
. u7 T9 f4 D, l3 Q7 j* _9 @<P>15.tmpfile()9 j, n& Q1 f3 C7 q( S/ b
  其原型是FILE *tmpfile(void); 生成一个临时文件,以"w+b"的模式打开,并返回这个临时流的指针,如果失败返回NULL。在程序结束时,这个文件会被自动删除。</P>/ @# |+ e$ v: u; N, B; ~! R( r
<P>例:FILE *fp=tmpfile();</P>
  w+ Y4 [% c  g# Y) X<P>16.tmpnam();3 @  g: R: H2 K8 \; k  ?% S8 ?# h
  其原型为char *tmpnam(char *s); 生成一个唯一的文件名,其实tmpfile()就调用了此函数,参数s用来保存得到的文件名,并返回这个指针,如果失败,返回NULL。</P>8 O5 ^, C! Z# x: \
' n5 a- d. n9 ]5 |
<P>9 ]/ O# O. U+ F
</P>
zan
转播转播0 分享淘帖0 分享分享0 收藏收藏0 支持支持0 反对反对0 微信微信
您需要登录后才可以回帖 登录 | 注册地址

qq
收缩
  • 电话咨询

  • 04714969085
fastpost

关于我们| 联系我们| 诚征英才| 对外合作| 产品服务| QQ

手机版|Archiver| |繁體中文 手机客户端  

蒙公网安备 15010502000194号

Powered by Discuz! X2.5   © 2001-2013 数学建模网-数学中国 ( 蒙ICP备14002410号-3 蒙BBS备-0002号 )     论坛法律顾问:王兆丰

GMT+8, 2025-9-17 20:34 , Processed in 0.652127 second(s), 51 queries .

回顶部