第3回 きちっとそろえましょ



パス名やファイル名は、関数に渡したり表示したりする前に、あらかじめ文字列を整えた形にしておきたいことがあります。そんなとき、どのような処理をさせればよいかを今回考えてみたいと思います。


[トップページ] / [CによるMS-DOSプログラミング]


【パス名を統一する】

第1回で少し触れましたが、

A:\DIR
A:\DIR\

の2通りのパスの記述方法を考慮してプログラミングしたほうがよいでしょう。ドキュメントに「A:\DIR\ という記述方法は認めない」と書いてしまえばそれまでですが、両方に対応させれば気にする必要がなくなります。

ここでは、上の「A:\DIR」に統一するようなプログラムを考えます。

/* SAMPLE06.C */

#include <stdio.h>
#include <string.h>
#include <jctype.h>

int main( int argc, char *argv[] )
{
    char path_name[ 81 ];
    char *ppath = path_name;
    
    if( argc < 2 || strlen( argv[ 1 ] ) > 80 ) return 1;
    
    strcpy( path_name, argv[ 1 ] );
    strupr( path_name );
    
    /* 文字列の終端にポインタをセット */
    ppath = strchr( path_name, '\0' );
    
    if( *--ppath == '\\' && *--ppath != ':'
    && iskanji( *ppath ) == 0 )
        *++ppath = '\0';
    
    printf( "%s\n", path_name );
    return 0;
}

A>SAMPLE06 A:\DIR\

とすると、「A:\DIR」と表示します。

単純に最後の'\'を除去するだけかというと、そうではありません。

if( *--path == '\\' && *--ppath != ':' ...

は、何をしているのでしょう。まず、文字列の終端記号の直前が'\'であるかどうかを調べ、さらにその前が':'以外であり、なおかつ全角文字の第1バイト以外であれば、'\'を'\0'に書き換える処理をしています。

':'であったときは、例えば

A:\

という文字列と考えることができます。この場合は'\'は取り除く必要はありません。

全角文字の第1バイト以外かどうかを調べるのには理由があります。例を挙げると、

A:\表

というパスがあった場合、「表」の第2バイトは'\'と同じなので、'\'かどうかというチェックに引っかかってしまいます。この場合も無視しなくてはなりません。

全角文字を扱うときにはよく起こる問題なので、常に頭に入れておく必要があります。


【ファイル名をそろえる】

ファイルやディレクトリの一覧表示をしたいときに

HOGEHOGE.TXT
HO.TXT
HOGE.TXT

だと、何となく見づらい気がします(いや、実際見づらい)。MS-DOSでは、ファイル名は8文字まで、拡張子は3文字までと決まっているので、

HOGEHOGE.TXT
HO      .TXT
HOGE    .TXT

というようにピリオドでそろえると見栄えがいいと思いませんか?

では、プログラムです。

/* SAMPLE07.C */

#include <stdio.h>
#include <string.h>

int main( int argc, char *argv[] )
{
    char file_name[ 13 ];
    char *pfile = file_name;
    int i = 0, j;
    
    if( argc < 2 || strlen( argv[ 1 ] ) > 12 ) return 1;
    
    if( argv[ 1 ][ 0 ] != '.' )
        strcpy( file_name, argv[ 1 ] );
    else
    {
        while( argv[ 1 ][ i ] )
        {
            /* ピリオドならば、スペースを入れてからコピー */
            if( argv[ 1 ][ i ] == '.' )
            {
                for( j = i; j < 8; j++ )
                    *pfile++ = ' ';
                *pfile++ = '.';
            }
            /* ピリオドでなければ、そのままコピー */
            else *pfile++ = argv[ 1 ][ i ];
            i++;
        }
        *pfile = '\0';
    }
    printf( "%s\n", file_name );
    return 0;
}

A>SAMPLE07 HOGE.TXT

とすれば、「HOGE  .TXT」と表示されます。

最初に、先頭文字が'.'かどうかを調べているのは、「.」(カレントディレクトリ)と「..」(親ディレクトリ)は省くという意味です。MS-DOSには、ピリオドから始まるファイルはありませんから、このときは空白は入れないことにしました。

拡張子も合わせて12文字までという制限は、普段は短くて不便に思うことがあるかもしれません。でも、プログラムを組む上では、設計がしやすくてありがたいものです。


[トップページ] / [CによるMS-DOSプログラミング]