● 関数リファレンス

区切り文字間にある文字列の取得

    char * __stdcall   StrCalc_getword(char *pstr,char *pdest,int len,char *ppstart);

引数

引数名意味
pstr走査開始アドレス
pdest発見した文字列を格納するバッファのアドレス
lenpdest が指すバッファのサイズ
ppstartコピーを開始した位置(NULL指定可)

戻り値

走査を停止した位置を返します。

説明

pstr の中にある、StrCalc の区切り文字で区切られている文字列を pdest にコピーします。
コピーした文字列には、末尾にヌル文字が付加されます。

pstr からコピー対象文字までの間にある、空白・タブ文字・区切り文字は無視されます。対象文字列の中にある空白・タブ文字は詰められますが、シングルクォートで括られた範囲はそのままコピーされます。
コピーした文字列長が len - 1 に達した場合は、コピーできなかった文字の位置で走査を終了します。

ppstart には、コピー開始位置を指すポインタが返されます。pstr 〜 末尾ヌルまでの間にコピーできる文字列が無かった場合は、戻り値と同じ位置を返します。
pstr*ppstart には、無視された区切り文字が存在する場合があり、プログラムがこの内容を必要とする場合は、ppstart で返されたポインタを使って処理する事ができます(テスト2参照の事)。


テスト1.

#include <stdio.h>
#include "sc39.h"

void    main(void)
{
    char            *ptr = "abs((1 2 3 4 5 + 72) * 8 - int  max) + 1234567890123456789012345678901234 + abcdefg\thijklmnop\tqrstu \t vwxyz1234567";
    char            dest[SC_MAX_PARAMNAME+1];
    char            septbl[256];
    int             i;

    i = 0;
    do{
        septbl[i] = (char)StrCalc_issep(i);
    }while(++i < 256);

    do{
        /* 区切り文字の間にある文字列を dest にコピー */
        ptr = StrCalc_getword(ptr,dest,sizeof(dest),NULL);
        if (*dest){
            printf("%s",dest); /* コピーした内容を表示 */

            /*
              スキャン停止した位置の文字が区切り文字でなかった場合はバッファ
              フル。この場合は SC_MAX_PARAMNAME(33文字)を超えている事にな
              るので、StrCalc の数値・関数名・定数名・変数名としては長過ぎる。
            */
            if (!septbl[*ptr])
                printf("    長過ぎる");

            printf("\n");
        }
    }while(*ptr);
}


実行結果.

abs
12345
72
8
intmax
123456789012345678901234567890123    長過ぎる
4                                              ← コピーしきれなかった分
abcdefghijklmnopqrstuvwxyz1234567



テスト2.該当する文字列を single character memory に置換する

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

typedef struct {
    char        name[SC_MAX_PARAMNAME+1];
    unsigned    chr_index;
} SEARCHTBL,*PSEARCHTBL;

/* 置換テーブル */
SEARCHTBL           table[] = {
    { "abs", 0 },                               /* ア */
    { "12345", 1 },                             /* イ */
    { "72", 2 },                                /* ウ */
    { "8", 3 },                                 /* エ */
    { "123456789012345678901234567890123", 1 }, /* イ */
    { "abcdefghijklmnopqrstuvwxyz1234567", 5 }  /* カ */
};

void    main(void)
{
    char            *ptr = "abs((1 2 3 4 5 + 72) * 8 - int  max) + 123456789012345678901234567890123 + abcdefg\thijklmnop\tqrstu \t vwxyz1234567";
    char            *p1,*p2,*pdest,chk[SC_MAX_PARAMNAME+1],buf[512];
    int             len,i;

    /*
      切り出される文字列は最低でも1バイトはあるので、single character memory に
      置き換えても「全体の長さ ≦ 元の文字列長」となります。
    */

    pdest = buf;
    do{
        p2 = StrCalc_getword(ptr,chk,sizeof(chk),&p1);

        /*
          コピー開始位置までの間に文字列がある場合は、
          バッファにコピーする
        */
        if ((len = p1 - ptr) > 0)
            pdest = (char *)memcpy(pdest,ptr,len) + len;

        if (!*chk) continue;

        /* 置換テーブルから対象の文字列を検索 */
        i = sizeof(table) / sizeof(SEARCHTBL) - 1;
        do{
            if (!_stricmp(chk,table[i].name)) break;
        }while(--i >= 0);

        if (i < 0){
            /*
              該当文字列が見付からなかった場合は、
              切り出された文字列をそのまま貼り付ける
            */
            pdest = (char *)memcpy(pdest,chk,len = strlen(chk)) + len;
        }else{
            /*
              該当文字列が見付かった場合は、
              対応する single character memory を貼り付ける
            */
            *pdest++ = (unsigned char )(table[i].chr_index + 'ア');
        }
    }while(*(ptr = p2));
    *pdest = 0;

    printf("%s\n",buf); /* 結果の表示 */
}


実行結果.

ア((イ+ ウ) * エ- intmax) + イ+ カ