คล้ายกับฟังก์ชันExplode () ที่ Mef นำเสนอ แต่มีข้อแตกต่างสองสามประการ (ซึ่งหนึ่งในนั้นฉันถือว่าเป็นการแก้ไขข้อบกพร่อง):
type
TArrayOfString = array of String;
function SplitString(const aSeparator, aString: String; aMax: Integer = 0): TArrayOfString;
var
i, strt, cnt: Integer;
sepLen: Integer;
procedure AddString(aEnd: Integer = -1);
var
endPos: Integer;
begin
if (aEnd = -1) then
endPos := i
else
endPos := aEnd + 1;
if (strt < endPos) then
result[cnt] := Copy(aString, strt, endPos - strt)
else
result[cnt] := '';
Inc(cnt);
end;
begin
if (aString = '') or (aMax < 0) then
begin
SetLength(result, 0);
EXIT;
end;
if (aSeparator = '') then
begin
SetLength(result, 1);
result[0] := aString;
EXIT;
end;
sepLen := Length(aSeparator);
SetLength(result, (Length(aString) div sepLen) + 1);
i := 1;
strt := i;
cnt := 0;
while (i <= (Length(aString)- sepLen + 1)) do
begin
if (aString[i] = aSeparator[1]) then
if (Copy(aString, i, sepLen) = aSeparator) then
begin
AddString;
if (cnt = aMax) then
begin
SetLength(result, cnt);
EXIT;
end;
Inc(i, sepLen - 1);
strt := i + 1;
end;
Inc(i);
end;
AddString(Length(aString));
SetLength(result, cnt);
end;
ความแตกต่าง:
- พารามิเตอร์ aMax จำกัด จำนวนสตริงที่จะส่งคืน
- หากสตริงอินพุตถูกยกเลิกโดยตัวคั่นจะถือว่าสตริงสุดท้าย "ว่าง" ระบุมีอยู่
ตัวอย่าง:
SplitString(':', 'abc') returns : result[0] = abc
SplitString(':', 'a:b:c:') returns : result[0] = a
result[1] = b
result[2] = c
result[3] = <empty string>
SplitString(':', 'a:b:c:', 2) returns: result[0] = a
result[1] = b
มันเป็นตัวคั่นต่อท้ายและ "องค์ประกอบสุดท้ายที่ว่างเปล่า" เชิงสัญลักษณ์ที่ฉันพิจารณาแก้ไขข้อบกพร่อง
ฉันยังรวมการเปลี่ยนแปลงการจัดสรรหน่วยความจำที่ฉันแนะนำด้วยการปรับแต่ง (ฉันแนะนำผิดพลาดว่าสตริงอินพุตส่วนใหญ่อาจมีตัวคั่น 50% แต่แน่นอนว่าอาจประกอบด้วยสตริงตัวคั่น 100% ทำให้อาร์เรย์ขององค์ประกอบว่างเปล่า!)