안녕하세요?
utf8문자열을 자르다가 한가지 애로가 생겨 질문을 올립니다.
특정문자열을 기준으로 잘라내기를 반복하는데요 pos, posex가 문제입니다.
이 함수들이 ansistring용이여서 이것으로 계산한 문자열의 길이가 실제길이보다 커집니다.
제가 작업하는 중문체계에서 보면 한글 한글자는 한문자로 계산되는데 중문한자하나는 두문자로 계산됩니다.
결국 잘라낸 문자열의 꼬리에 포함된 한자개수만큼 뒤에 있는 글자들이 더 붙습니다.
예를 들면
<!--CodeS-->
vstr := '<ss>친구朋友friend</ss>';
bb := pos('<ss>', vstr) + 4;
ee := posex('</ss>', vstr, bb);
res := copy(vstr, bb, ee - bb);
<!--CodeE-->
로 자르면 친구朋友friend가 아니라 친구朋友friend</가 나옵니다.
editplus나 ulyraedit에서 character count를 해보면 유니코드로 센 문자수와 앤시로 센 문자수를 정확히 주던데 유니코드문자열에서 정확히 동작하는 pos, posex가 없을가요?
vstr := '
bb := pos('
bb := pos('
res := copy(vstr, bb, ee - bb);
혼용된 문자에서 중간중간을 삭제시
widestring 함수는 여러분들이 만들어 올린 함수들도 많아요.
그런데 어짜피 사용시 연결된 함수와 다양한 기능을 하려면 편하게 TNT컴포 사용하는게 나을지도 몰라요.
아니면, 컴포는 사용하지 않더라도 tnt에서 TntWideStrUtils나 TntWideStrings등 유닛만을 변형해서 사용하셔도 될거 같아요
아래는 tnt컴포에서 나온 함수입니다.
또는 여기 팁에보면 한글을 자를 때 깨지지 않게하는 것도 많이 올라와 있습니다
function WStrPos(Str, SubStr: PWideChar): PWideChar;
var
PSave: PWideChar;
P: PWideChar;
PSub: PWideChar;
begin
// returns a pointer to the first occurance of SubStr in Str
Result := nil;
if (Str <> nil) and (Str^ <> #0) and (SubStr <> nil) and (SubStr^ <> #0) then begin
P := Str;
While P^ <> #0 do begin
if P^ = SubStr^ then begin
// investigate possibility here
PSave := P;
PSub := SubStr;
While (P^ = PSub^) do begin
Inc(P);
Inc(PSub);
if (PSub^ = #0) then begin
Result := PSave;
exit; // found a match
end;
if (P^ = #0) then
exit; // no match, hit end of string
end;
P := PSave;
end;
Inc(P);
end;
end;
end;