システム・プログラム 電子・情報工学系 新城 靖 <yas@is.tsukuba.ac.jp>
このページは、次の URL にあります。
http://www.hlla.is.tsukuba.ac.jp/~yas/coins/syspro-2000/2000-04-24
/file-lib.html
あるいは、次のページから手繰っていくこともできます。
http://www.hlla.is.tsukuba.ac.jp/~yas/coins/
http://www.is.tsukuba.ac.jp/~yas/index-j.html
---------------------------------------------------------------------- 1: /* 2: filter-char.c -- 文字単位の簡単なフィルタ 3: ~yas/syspro1//file/filter-char.c 4: $Header: /home/lab2/OS/yas/syspro1/file/RCS/filter-char.c,v 1.4 1998/04/27 16:41:23 yas Exp $ 5: Start: 1997/04/21 18:23:13 6: */ 7: 8: #include <stdio.h> /* stdin, stdout, fopen(), fclose(), getc(), */ 9: #include <ctype.h> /* toupper() */ 10: 11: extern void filter_char_upper( FILE *in, FILE *out ); 12: 13: main( int argc, char *argv[] ) 14: { 15: int i ; 16: FILE *fp ; 17: if( argc == 1 ) 18: filter_char_upper( stdin, stdout ); 19: else 20: { 21: for( i=1 ; i< argc ; i++ ) 22: { 23: if( (fp = fopen( argv[i],"r" )) == NULL ) 24: { 25: perror( argv[i] ); 26: exit( -1 ); 27: } 28: filter_char_upper( fp, stdout ); 29: fclose( fp ); 30: } 31: } 32: } 33: 34: void filter_char_upper( FILE *in, FILE *out ) 35: { 36: int c ; /* int型。char は、不可 */ 37: while( (c=getc(in)) != EOF ) 38: { 39: putc( toupper(c),out ); 40: } 41: } ----------------------------------------------------------------------
実行例
---------------------------------------------------------------------- % ./filter-charabc
ABC asdfjkl;
ASDFJKL; ^D %
----------------------------------------------------------------------
fopen()は、ファイルを開くライブラリ関数である。"r" は、 読み込み専用で ファイルを開くことを意味している。fopen()は、結果として FILE 構造体へ のポインタを返す。これは、stdio.h で宣言されている配列 _iob[] の要素へ のポインタである。これは、次のようなライブラリ関数で使われる。
fgetc() fputs() getc() getw() fgets() fread() ungetc() fprintf() fscanf() fputc() fwrite() putc() putc() fflush() fseek() ftell() frewind() fclose() fdopen() freopen() ferrror() feof() clearerr() fileno()
このような、struct FILE を使うライブラリ関数群は、次のような名前で呼ば れる。
putc() は、第1引数で指定された文字を第2引数で与えられたストリームへ 出力する。
fclose() は、ファイルを閉じるライブラリ関数である。
Java 風に書くとこうなる。
class FILE { int fgetc(); int fputs(String str); size_t fread(byte buf, size_t size, size_t nmemb); ... } FILE stdin ; FILE stdout ; int x = stdin.fgetc(); stdout.fputs("hello");引数の FILE *stream が、オブジェクトとなり、普通の引数からは消える。呼 出しの時には、オブジェクトを指定する。
---------------------------------------------------------------------- 1: /* 2: filestruct-print.c -- _filestruct[] の内容を表示する 3: ~yas/syspro1/file/filestruct-print.c 4: $Header: /home/lab2/OS/yas/syspro1/file/RCS/filestruct-print.c,v 1.3 1998/04/27 16:59:12 yas Exp $ 5: Start: 1997/05/05 18:31:55 6: */ 7: 8: #include <stdio.h> 9: 10: #if 0 11: typedef struct { 12: int _cnt; 13: unsigned char *_ptr; 14: unsigned char *_base; 15: unsigned short _flag; 16: unsigned char _flag; 17: unsigned char _file; 18: } FILE; 19: extern FILE __iob[100 ]; 20: #endif 21: 22: extern void filestruct_print( FILE *fp ); 23: 24: main() 25: { 26: FILE *fp ; 27: 28: printf("stdin == 0x%x == &_iob[%d]\n",stdin, stdin-&__iob[0] ); 29: printf("stdout == 0x%x == &_iob[%d]\n",stdout, stdout-&__iob[0] ); 30: printf("stderr == 0x%x == &_iob[%d]\n",stderr, stderr-&__iob[0] ); 31: 32: fp = fopen("filestruct-print.c","r"); 33: printf("fp == 0x%x == &__iob[%d]\n",fp, fp-&__iob[0] ); 34: 35: printf("fopen()\n"); 36: filestruct_print( fp ); 37: getc( fp ); 38: printf("getc()\n"); 39: filestruct_print( fp ); 40: getc( fp ); 41: printf("getc()\n"); 42: filestruct_print( fp ); 43: fclose( fp ); 44: printf("fclose()\n"); 45: filestruct_print( fp ); 46: } 47: 48: 49: void filestruct_print( FILE *fp ) 50: { 51: printf("cnt:%d, ptr:0x%x, base:0x%x, flag:0%x, flag:%d, file:%d\n", 52: fp->_cnt, fp->_ptr, fp->_base, fp->_flag, 53: fp->_flag,fp->_file); 54: } ---------------------------------------------------------------------- #define getc(p) (--(p)->_cnt < 0 ? __filbuf(p) : (int)*(p)->_ptr++) ----------------------------------------------------------------------
---------------------------------------------------------------------- % make filestruct-printcc filestruct-print.c -o filestruct-print % ./filestruct-print
stdin == 0xfb4f044 == &_iob[0] stdout == 0xfb4f054 == &_iob[1] stderr == 0xfb4f064 == &_iob[2] fp == 0xfb4f074 == &__iob[3] fopen() cnt:0, ptr:0x0, base:0x0, flag:01, flag:1, file:3 getc() cnt:1252, ptr:0x10002009, base:0x10002008, flag:09, flag:9, file:3 getc() cnt:1251, ptr:0x1000200a, base:0x10002008, flag:09, flag:9, file:3 fclose() cnt:0, ptr:0x0, base:0x0, flag:00, flag:0, file:3 %
----------------------------------------------------------------------
高水準入出力ライブラリ関数を持ちいて、次のようなフィルタを作りなさい。
入力: ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz 出力: NOPQRSTUVWXYZABCDEFGHIJKLM nopqrstuvwxyzabcdefghijklmそれ以外のものは、そのまま出力する。この暗号法を rot13 (rotation)とい う。これは、まったく同じルーチンで暗号化と復号化ができる。 ネットワーク・ニュースなでど、ネタばらしの投稿に使われる。