C言語strシリーズライブラリ関数のstrspn()、strcspn()およびstrpbrk()
vc++8.0の関数ライブラリでは、strtok()関数の実装にbit mapが採用され、strspn()、strcspn()、strpbrk()の3つの関数ソースコードを引き続き調べ、bit mapも採用されて記憶空間を減らし、一部のコードを共通化していることが分かったので、ブロガーを書いて簡単に記録します.
まず、3つの関数のプロトタイプを見てみましょう.
XXMicrosoft Visual Studio 8VCcrtsrcこのフォルダの下にはstrcspnという3つのファイルがあります.c、strpbrk.cとstrspn.c.
strcspn.c:
strpbrk.c:
重要な実現はstrspn.c中:
strtok()のソースコードを理解すると、この3つの関数の理解が容易すぎて、主にビットマップの使用で、C++の中で専門の標準タイプbitsetを提供して、巧みに使用して、多くのアルゴリズムの中で空間を節約することができて、効率を高めることができます.
まず、3つの関数のプロトタイプを見てみましょう.
//return length of prefix of string consisting of characters in control
size_t __cdecl strspn (const char * string, const char * control);
//return length of prefix of string consisring of characters not in control
size_t __cdecl strcspn (const char * string, const char * control);
//return pointer to first occurrence in string of any charactrers of control,
//or NULL if nor present
char * __cdecl strpbrk (const char * string, const char * control);
XXMicrosoft Visual Studio 8VCcrtsrcこのフォルダの下にはstrcspnという3つのファイルがあります.c、strpbrk.cとstrspn.c.
strcspn.c:
#define SSTRCSPN //
#include "strspn.c"
strpbrk.c:
#define SSTRPBRK //
#include "strspn.c"
重要な実現はstrspn.c中:
/* Determine which routine we're compiling for (default to STRSPN) */
#define _STRSPN 1
#define _STRCSPN 2
#define _STRPBRK 3
#if defined (SSTRCSPN)
#define ROUTINE _STRCSPN
#elif defined (SSTRPBRK)
#define ROUTINE _STRPBRK
#else
#define ROUTINE _STRSPN //
#endif
/* Routine prototype */
#if ROUTINE == _STRSPN
size_t __cdecl strspn (
#elif ROUTINE == _STRCSPN
size_t __cdecl strcspn (
#else /* ROUTINE == _STRCSPN */
char * __cdecl strpbrk (
#endif /* ROUTINE == _STRCSPN */
const char * string,
const char * control
)
{
const unsigned char *str = string;
const unsigned char *ctrl = control;
unsigned char map[32];
int count;
/* Clear out bit map */
for (count=0; count<32; count++)
map[count] = 0;
/* Set bits in control map */
while (*ctrl) // strtok()
{
map[*ctrl >> 3] |= (1 << (*ctrl & 7));
ctrl++;
}
#if ROUTINE == _STRSPN // strspn()
/* 1st char NOT in control map stops search */
if (*str)
{
count=0;
while (map[*str >> 3] & (1 << (*str & 7)))
{
count++;
str++;
}
return(count);
}
return(0);
#elif ROUTINE == _STRCSPN //strcspn()
/* 1st char in control map stops search */
count=0;
map[0] |= 1; /* null chars not considered */
while (!(map[*str >> 3] & (1 << (*str & 7))))
{
count++;
str++;
}
return(count);
#else /* ROUTINE == _STRCSPN */ //strpbrk()
/* 1st char in control map stops search */
while (*str)
{
if (map[*str >> 3] & (1 << (*str & 7)))
return((char *)str);
str++;
}
return(NULL);
#endif /* ROUTINE == _STRCSPN */
}
strtok()のソースコードを理解すると、この3つの関数の理解が容易すぎて、主にビットマップの使用で、C++の中で専門の標準タイプbitsetを提供して、巧みに使用して、多くのアルゴリズムの中で空間を節約することができて、効率を高めることができます.