Rui Ueyama
rui31****@gmail*****
2006年 11月 20日 (月) 12:25:39 JST
マルチバイト文字列のサブストリング作成、string pointer作成を 少し改良しました。 元のコードでは、新たに作成するサブストリングの末尾の位置を 調べるために文字列をスキャンしていました。変更後のコードでは、 文字列末尾までのサブストリングは元の文字列と末尾位置が同じ であることを利用して、この場合に文字列のスキャンを行いません。 string pointerの改良も同様です。 長いマルチバイト文字列の末尾までのサブストリング作成を繰り 返す場合や、内部的にstring pointerを使っているSRFI-13の 手続きにマルチバイト文字列を渡しているようなコードで、速度 向上が見られるようです。 -- 植山 類 -------------- next part -------------- Index: src/string.c =================================================================== RCS file: /cvsroot/gauche/Gauche/src/string.c,v retrieving revision 1.78 diff -u -B -r1.78 string.c --- src/string.c 8 Nov 2006 13:41:48 -0000 1.78 +++ src/string.c 20 Nov 2006 03:19:08 -0000 @@ -856,12 +856,9 @@ static ScmObj substring(const ScmStringBody *xb, int start, int end) { - if (start < 0) - Scm_Error("start argument needs to be positive: %d", start); - if (end > SCM_STRING_BODY_LENGTH(xb)) - Scm_Error("end argument is out of range: %d", end); - if (end < start) - Scm_Error("end argument must be equal to or greater than the start argument: start=%d, end=%d", start, end); + int len = SCM_STRING_BODY_LENGTH(xb); + SCM_CHECK_START_END(start, end, len); + if (SCM_STRING_BODY_SINGLE_BYTE_P(xb)) { return SCM_OBJ(make_str(end-start, end-start, @@ -871,7 +868,9 @@ const char *s, *e; if (start) s = forward_pos(SCM_STRING_BODY_START(xb), start); else s = SCM_STRING_BODY_START(xb); - e = forward_pos(s, end - start); + if (len == end) + e = SCM_STRING_BODY_START(xb) + SCM_STRING_BODY_SIZE(xb); + else e = forward_pos(s, end - start); return SCM_OBJ(make_str(end - start, e - s, s, 0)); } } @@ -1365,7 +1364,9 @@ } else { sptr = forward_pos(SCM_STRING_BODY_START(srcb), start); ptr = forward_pos(sptr, index); - eptr = forward_pos(sptr, end - start); + if (end == len) + eptr = SCM_STRING_BODY_START(srcb) + SCM_STRING_BODY_SIZE(srcb); + else forward_pos(sptr, end - start); effective_size = eptr - ptr; } sp = SCM_NEW(ScmStringPointer);