線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:5527
推到 Plurk!
推到 Facebook!

如何快速取出字串中的某一段子字串 ??

答題得分者是:aquarius
ANDY8C
資深會員


發表:114
回覆:582
積分:299
註冊:2006-10-29

發送簡訊給我
#1 引用回覆 回覆 發表時間:2004-12-08 13:43:26 IP:211.74.xxx.xxx 未訂閱
在字串的分析上,常會讀取某一段子字串的需求 #1111#22#333#4444#55555#6#7#88###ABCD........... 我的需求是要取字串中的某一小段字串,例如:要取第四個分隔符號後的字串 4444, 我的做法是由左讀到右,當讀取到第四個 # 後,才取出 4444 ,感覺不是很好的寫法 萬一要讀第 nnn 個分隔符號後的字串 ,那程式會很浪費時間的..... 不知網友有更精簡的寫法嗎 ? 以下是我部分的程式片段,大家集思廣義.... // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // 分割及取出 TEC Command 字串 // instr ==> 要處理的原始字串,最後的字元最好都加原始分割字元 // Old_Pstr ==> 原始分割字元 // New_Pstr ==> 新的分割替代字元(為了完整取出原始字串) // Get_tag_no ==> 要第幾個取出 Tag ,本分割字元左邊算來第幾個 // tag_len ==> 該取出 Tag 字串長度 // 傳回值 : 某一個特定的分隔字元後的那一串文字 // 若無此 tag_no 或超過實際 tag_no 最大數值, 則傳回 Error function Parse_Substring( inStr:String; Old_Pstr:string; New_Pstr:string; Get_tag_no:Integer; Get_tag_len:Integer):string; var tag_str : string tag_no,j,nPos_now,nPos_next ,ni : Integer; begin // 傳入變數 Pstr 的長度,不可以大於 sParse 的長度 tag_no := 0; nPos_next := 0; // 判斷最後的字元,是否為分隔字元,不是的話,自動附加上,方便程式計算 ni := length(Old_Pstr); if not (Old_Pstr = copy( instr, (length(instr)-ni) 1,ni)) then instr := instr Old_Pstr; while pos(Old_Pstr,inStr) > 0 do begin nPos_now := pos(Old_Pstr,inStr); // 不同長度, Old_Pstr 判斷 if (nPos_now > 0) and (copy(instr,nPos_now,ni)=Old_Pstr) then begin tag_str := copy(inStr,nPos_Next 1,nPos_now-nPos_Next-1); if tag_no = Get_tag_no then begin RESULT := copy(tag_str,1,Get_tag_len); // 取需要的字串長度 exit; end; nPos_Next := nPos_now ni-1; tag_no := tag_no 1; end; // 分割字元替換處理,可替換一個字元以上 for j := 1 to length(Old_Pstr) do inStr[nPos_now j-1] := New_Pstr[j]; end; RESULT := 'STRING ERROR : (0000) 參數的內容太少或型態錯誤 !! ' #13#10 '(Parse)->' instr #13#10; // 有錯誤發生 end; = = = == = = = = = = = = = == == = = = = = = = = = = = = = = = = 不知網友有更精簡的寫法嗎 ? -------------------------------- 這一網站,真的不錯!! 發表人 - ANDY8C 於 2004/12/08 13:50:49 發表人 - ANDY8C 於 2004/12/08 14:08:43 發表人 - ANDY8C 於 2004/12/08 14:09:36
------
---------------------------------------
偶爾才來 KTOP ,交流條碼問題,在 FB [條碼標籤達人] 社團留言,感恩.
shieh2700
高階會員


發表:0
回覆:127
積分:100
註冊:2002-06-13

發送簡訊給我
#2 引用回覆 回覆 發表時間:2004-12-08 14:09:46 IP:61.229.xxx.xxx 未訂閱
procedure TForm1.Button1Click(Sender: TObject);
begin
  ShowMessage( Split( '#1111#22#333#4444#55555#6#7#88###ABCD', '#' )[4] );
end;    function Split(s, delimiter: string): TStrings;
var rs : TStrings;
begin
  rs := TStringList.Create;
  rs.Text := StringReplace( s, delimiter, #13, [rfReplaceAll, rfIgnoreCase] );
  Result := rs;
end;
jow
尊榮會員


發表:66
回覆:751
積分:1253
註冊:2002-03-13

發送簡訊給我
#3 引用回覆 回覆 發表時間:2004-12-09 11:22:56 IP:220.130.xxx.xxx 未訂閱
shieh2700,你好!你的程式碼可以Work,但是有一點點小問題,就是Split回傳的TStringList,每次使用後都沒有被釋放掉,個人做了些許修改
procedure TForm1.Button1Click(Sender: TObject);
var
  S: TStrings;
begin
  S := Split('#1111#22#333#4444#55555#6#7#88###ABCD','#');
  try
    if Assigned(S) then ShowMessage(S[4]);
  finally
    FreeAndNil(S);
  end;
end;    function Split(s, delimiter: string): TStrings;
begin
  Result := TStringList.Create;
  Resultrs.Text := StringReplace(s,delimiter,#13,[rfReplaceAll, rfIgnoreCase]);
end;    
shieh2700
高階會員


發表:0
回覆:127
積分:100
註冊:2002-06-13

發送簡訊給我
#4 引用回覆 回覆 發表時間:2004-12-09 14:58:27 IP:61.229.xxx.xxx 未訂閱
jow 前輩, 感謝您的指正.
aquarius
資深會員


發表:3
回覆:347
積分:330
註冊:2003-05-21

發送簡訊給我
#5 引用回覆 回覆 發表時間:2004-12-09 18:02:38 IP:210.243.xxx.xxx 未訂閱
可以用 strpos 加速. 至於用 TStrings, 看起來簡潔, 但運算時間反而大增, 因為還要做一大堆create物件的相關動作.    參考下列的程式碼.     
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
// 分割及取出 TEC Command 字串
// instr ==> 要處理的原始字串,最後的字元最好都加原始分割字元
// Old_Pstr ==> 原始分割字元
// New_Pstr ==> 新的分割替代字元(為了完整取出原始字串)
// Get_tag_no ==> 要第幾個取出 Tag ,本分割字元左邊算來第幾個
// tag_len ==> 該取出 Tag 字串長度
// 傳回值 : 某一個特定的分隔字元後的那一串文字
// 若無此 tag_no 或超過實際 tag_no 最大數值, 則傳回 Error
function Parse_Substring( inStr:String; Old_Pstr:string; New_Pstr:string; Get_tag_no:Integer; Get_tag_len:Integer):string;
var
  tag_str : string ;
  tag_no,j,nPos_now,nPos_next ,ni : Integer;
begin
  // 傳入變數 Pstr 的長度,不可以大於 sParse 的長度
  tag_no := 0;
  nPos_next := 0;
  // 判斷最後的字元,是否為分隔字元,不是的話,自動附加上,方便程式計算
  ni := length(Old_Pstr);      if not (Old_Pstr = copy( instr, (length(instr)-ni) 1,ni)) then
    instr := instr   Old_Pstr;      while pos(Old_Pstr,inStr) > 0 do
    begin
    nPos_now := pos(Old_Pstr,inStr);
    // 不同長度, Old_Pstr 判斷
    if (nPos_now > 0) and (copy(instr,nPos_now,ni)=Old_Pstr) then
      begin
      tag_str := copy(inStr,nPos_Next 1,nPos_now-nPos_Next-1);        if tag_no = Get_tag_no then
      begin
      RESULT := copy(tag_str,1,Get_tag_len); // 取需要的字串長度
      exit;
    end;        nPos_Next := nPos_now ni-1;
    tag_no := tag_no 1;
    end;      // 分割字元替換處理,可替換一個字元以上
  for j := 1 to length(Old_Pstr) do
    inStr[nPos_now j-1] := New_Pstr[j];
  end;      RESULT := 'STRING ERROR : (0000) 參數的內容太少或型態錯誤 !! ' #13#10 '(Parse)->' instr  #13#10; // 有錯誤發生    end;    function Split(s, delimiter: string): TStrings;
begin
  Result := TStringList.Create;
  Result.Text := StringReplace(s,delimiter,#13,[rfReplaceAll, rfIgnoreCase]);
end;    function NewParse_Substring(inStr:String; Old_Pstr:string; Get_tag_no:Integer; Get_tag_len:Integer):string;
var
  pc, pcNext, pcRet, pcTag : pchar ;
  i, iLen : integer ;
begin
  pc:=pchar(inStr) ;
  pcRet:=pc ;
  pctag:=pchar(Old_Pstr) ;
  for i:=1 to Get_tag_no do
    begin
    pcRet:=StrPos(pc,pcTag) ;
    if pcRet=nil then
      begin
      Result:='STRING ERROR : (0000) 參數的內容太少或型態錯誤 !! ' #13#10 '(Parse)->' instr  #13#10; // 有錯誤發生
      exit ;
      end ;
    pc:=pcRet 1 ;
    end ;
  pcNext:=StrPos(pc,pcTag) ;
  if pcNext=nil then
    pcNext:=StrEnd(pchar(Old_Pstr)) ;      i:=DWORD(pcNext)-DWORD(pc) ;
  Result:=copy(strpas(pc),1,i) ;
end ;    procedure TForm1.Button1Click(Sender: TObject);
var
  s, sRet : string ;
  i : integer ;
  dw : DWORD ;
begin
  s:='#1111#22#333#4444#55555#6#7#88###ABCD' ;
  Memo1.clear ;
  dw:=GetTickCount ;
  for i:=0 to 99999 do
    begin
    sRet:=NewParse_Substring(s,'#',i mod 13,10) ;
    end ;
  Memo1.Lines.Add(format('Time=%d',[GetTickCount-dw])) ;
end;    procedure TForm1.Button2Click(Sender: TObject);
var
  s, sRet : string ;
  i : integer ;
  dw : DWORD ;
begin
  s:='#1111#22#333#4444#55555#6#7#88###ABCD' ;
  Memo1.clear ;
  dw:=GetTickCount ;
  for i:=0 to 99999 do
    begin
    sRet:=Parse_Substring(s,'#','-',i mod 13,10) ;
    end ;
  Memo1.Lines.Add(format('Time=%d',[GetTickCount-dw])) ;
end;    procedure TForm1.Button3Click(Sender: TObject);
var
  sl : TStrings ;
  s, sRet : string ;
  i : integer ;
  dw : DWORD ;
begin
  s:='#1111#22#333#4444#55555#6#7#88###ABCD' ;
  Memo1.clear ;
  dw:=GetTickCount ;
  for i:=0 to 99999 do
    begin
    sl:=Split(s,'#');
    try
      if Assigned(sl) then
        if (i mod 13)        ...Aquarius
        
------
水瓶男的blog: http://791909.blogspot.com
jow
尊榮會員


發表:66
回覆:751
積分:1253
註冊:2002-03-13

發送簡訊給我
#6 引用回覆 回覆 發表時間:2004-12-09 18:23:25 IP:220.130.xxx.xxx 未訂閱
如果是...
procedure TForm1.Button3Click(Sender: TObject);
var
  sl : TStrings ;
  s, sRet : string ;
  i : integer ;
  dw : DWORD ;
begin
  s:='#1111#22#333#4444#55555#6#7#88###ABCD' ;
  Memo1.clear ;
  dw:=GetTickCount ;

  sl:=Split(s,'#');
  try
    if Assigned(sl) then
      if s1.Count > 0 then
        for i:=0 to 99999 do
          sRet:=sl[i mod sl.count];
  finally
    FreeAndNil(sl);
  end ;      Memo1.Lines.Add(format('Time=%d',[GetTickCount-dw])) ;
end;     
我覺得shieh2700做法依舊可取的,見仁見智.    
shieh2700
高階會員


發表:0
回覆:127
積分:100
註冊:2002-06-13

發送簡訊給我
#7 引用回覆 回覆 發表時間:2004-12-10 05:44:17 IP:61.229.xxx.xxx 未訂閱
個人認為兩種做法各有其優缺點, 所以寫了支程式來模擬四種狀況, 突顯其間之差異:    【執行結果】 模擬四種狀況, 取十組資料, 每組各跑一萬次, 計算此兩種處理方式的處理時間 測試資料=00#11#22#33#44#55#66#77#88#99#00#11#22#33#44#55#66#77#88#99#00#11#22#33 #44#55#66#77#88#99#00#11#22#33#44#55#66#77#88#99#00#11#22#33#44#55#66#77#88#99# 分隔字元=# 模擬狀況一:只取第五個欄位         SubString:60,50,50,50,50,40,50,40,50,51,         Split    :1822,1873,1903,1882,1893,1873,1872,1883,1873,1862, 模擬狀況二:取得所有欄位         SubString:6350,6319,6329,6329,6339,6369,6399,6329,6320,6399,         Split    :1792,1843,1833,1842,1753,1732,1753,1752,1773,1752, 模擬狀況三:只取前二十個欄位         SubString:1372,1362,1362,1382,1382,1392,1362,1382,1362,1382,         Split    :1773,1762,1873,1903,1902,1893,1893,1873,1872,1893, 模擬狀況四:只取後二十個欄位         SubString:3615,3585,3636,3595,3585,3625,3585,3605,3606,3585,         Split    :1882,1863,1863,1863,1862,1803,1762,1773,1873,1882,    【測試程式】
program SplitTest;
{$APPTYPE CONSOLE}
uses
  SysUtils,
  classes,
  windows;    //jow
function Split(s, delimiter: string): TStrings;
begin
  Result := TStringList.Create;
  Result.Text := StringReplace(s,delimiter,#13,[rfReplaceAll, rfIgnoreCase]);
end;    //aquarius
function NewParse_Substring(inStr:String; Old_Pstr:string; Get_tag_no:Integer; Get_tag_len:Integer):string;
var
  pc, pcNext, pcRet, pcTag : pchar ;
  i, iLen : integer ;
begin
  pc:=pchar(inStr) ;
  pcRet:=pc ;
  pctag:=pchar(Old_Pstr) ;
  for i:=1 to Get_tag_no do
    begin
    pcRet:=StrPos(pc,pcTag) ;
    if pcRet=nil then
      begin
      Result:='STRING ERROR : (0000) 參數的內容太少或型態錯誤 !! ' #13#10 '(Parse)->' instr  #13#10; // 有錯誤發生
      exit ;
      end ;
    pc:=pcRet 1 ;
    end ;
  pcNext:=StrPos(pc,pcTag) ;
  if pcNext=nil then
    pcNext:=StrEnd(pchar(Old_Pstr)) ;
  i:=DWORD(pcNext)-DWORD(pc) ;
  Result:=copy(strpas(pc),1,i) ;
end ;    //處理狀況一:只取第五欄位
procedure test1(s,d:string);
var
  sRet : string ;
  ss:TStrings;
  i,j : integer ;
  dw : DWORD ;
begin
  Write(#9 'SubString:');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do
      sRet:=NewParse_Substring(s,d,5,10) ;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
  Write(#9 'Split    :');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      ss:=Split(s,d) ;
      try
        if Assigned(ss) then
          if ss.Count>=5 then
            sRet:=ss[5];
      finally
        FreeAndNil(ss);
      end ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
end;
//處理狀況二:取得所有欄位
procedure test2(s,d:string);
var
  sRet : string ;
  ss:TStrings;
  i,j,k : integer ;
  dw : DWORD ;
begin
  Write(#9 'SubString:');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      for k := 0 to 49 do
        sRet:=NewParse_Substring(s,d,k,10) ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
  Write(#9 'Split    :');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      ss:=Split(s,d) ;
      try
        if Assigned(ss) then
          for k := 0 to 49 do
            sRet:=ss[k];
      finally
        FreeAndNil(ss);
      end ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
end;
//處理狀況三:只取前二十個欄位
procedure test3(s,d:string);
var
  sRet : string ;
  ss:TStrings;
  i,j,k : integer ;
  dw : DWORD ;
begin
  Write(#9 'SubString:');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      for k := 0 to 19 do
        sRet:=NewParse_Substring(s,d,k,10) ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
  Write(#9 'Split    :');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      ss:=Split(s,d) ;
      try
        if Assigned(ss) then
          for k := 0 to 19 do
            sRet:=ss[k];
      finally
        FreeAndNil(ss);
      end ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
end;
//處理狀況四:只取後二十個欄位
procedure test4(s,d:string);
var
  sRet : string ;
  ss:TStrings;
  i,j,k : integer ;
  dw : DWORD ;
begin
  Write(#9 'SubString:');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      for k := 30 to 49 do
        sRet:=NewParse_Substring(s,d,k,10) ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
  Write(#9 'Split    :');
  for i:=0 to 9 do begin
    dw:=GetTickCount ;
    for j:=0 to 9999 do begin
      ss:=Split(s,d) ;
      try
        if Assigned(ss) then
          for k := 30 to 49 do
            sRet:=ss[k];
      finally
        FreeAndNil(ss);
      end ;
    end;
    Write(format('%d,',[GetTickCount-dw]));
  end;
  WriteLn('');
end;    var
  testData: string;
begin
  // Insert user code here
  testData := '00#11#22#33#44#55#66#77#88#99#';
  testData := testData testData testData testData testData;
  Writeln(#13 '模擬四種狀況, 取十組資料, 每組各跑一萬次, 計算此兩種處理方式的處理時間');
  Writeln(#13 '測試資料=' testData);
  Writeln(#13 '分隔字元=#');
  Writeln(#13 '模擬狀況一:只取第五個欄位');
  test1(testData,'#');
  Writeln(#13 '模擬狀況二:取得所有欄位');
  test2(testData,'#');
  Writeln(#13 '模擬狀況三:只取前二十個欄位');
  test3(testData,'#');
  Writeln(#13 '模擬狀況四:只取後二十個欄位');
  test4(testData,'#');
  WriteLn('處理完成...');
  readln;
end.
aquarius
資深會員


發表:3
回覆:347
積分:330
註冊:2003-05-21

發送簡訊給我
#8 引用回覆 回覆 發表時間:2004-12-10 10:11:22 IP:210.243.xxx.xxx 未訂閱
引言: 如果是...
procedure TForm1.Button3Click(Sender: TObject);
var
  sl : TStrings ;
  s, sRet : string ;
  i : integer ;
  dw : DWORD ;
begin
  s:='#1111#22#333#4444#55555#6#7#88###ABCD' ;
  Memo1.clear ;
  dw:=GetTickCount ;

  sl:=Split(s,'#');
  try
    if Assigned(sl) then
      if s1.Count > 0 then
        for i:=0 to 99999 do
          sRet:=sl[i mod sl.count];
  finally
    FreeAndNil(sl);
  end ;      Memo1.Lines.Add(format('Time=%d',[GetTickCount-dw])) ;
end;     
我覺得shieh2700做法依舊可取的,見仁見智.    
改成這樣當然 TStrings 會比較快, 因為省去了重新 Parsing 的時間, 就直接索引到需要的資料. 但是在實際運用時, 會呼叫 Parsing 一般都是用來讀入一個大的文字檔, 例如 .CSV檔, 再取出資料處理. 那麼 TStrings 就必需不斷的重新 Create / Free. ...Aquarius
------
水瓶男的blog: http://791909.blogspot.com
jow
尊榮會員


發表:66
回覆:751
積分:1253
註冊:2002-03-13

發送簡訊給我
#9 引用回覆 回覆 發表時間:2004-12-10 11:01:02 IP:220.130.xxx.xxx 未訂閱
引言: -------------------------------------------------------------------------------- 改成這樣當然 TStrings 會比較快, 因為省去了重新 Parsing 的時間, 就直接索引到需要的資料. 但是在實際運用時, 會呼叫 Parsing 一般都是用來[讀入一個大的文字檔, 例如 .CSV檔, 再取出資料處理. 那麼 TStrings 就必需不斷的重新 Create / Free. -------------------------------------------------------------------------------- 個人也是認為這樣,Parsing動作一次到位,並且我覺得以TStrings的方式處理檔案也相當適合的,
    function Split(s, delimiter: string): TStrings;
begin
  Result := TStringList.Create;
  Result.Text := StringReplace(s,delimiter,#13,[rfReplaceAll, rfIgnoreCase]);
end;    procedure TForm1.Button1Click(Sender: TObject);
var
  R, S: TStringList
begin
  if FileExists(A_FILENAME)then
  begin
    R := TStringList.Create;
    try
      R.LoadFromFile(A_FILENAME);
      S := Split(R.Text);
      try
        if Assigned(S) then
        begin
          .
          .
          .
        end;
      finally
        FreeAndNil(S);
      end;
    finally
      FreeAndNil(R);
    end;
  end;
end;    
我覺得程式碼簡潔並且較具彈性,個人淺見,有錯勿怪.
jow
尊榮會員


發表:66
回覆:751
積分:1253
註冊:2002-03-13

發送簡訊給我
#10 引用回覆 回覆 發表時間:2004-12-10 11:13:48 IP:220.130.xxx.xxx 未訂閱
procedure TForm1.Button1Click(Sender: TObject);
var
  R, S: TStringList
begin
  if FileExists(A_FILENAME)then
  begin
    R := TStringList.Create;
    try
      R.LoadFromFile(A_FILENAME);
      S := Split(R.Text,'#'); <--更正 
      try
        if Assigned(S) then
        begin
          .
          .
          .
        end;
      finally
        FreeAndNil(S);
      end;
    finally
      FreeAndNil(R);
    end;
  end;
end;
補充: (1)方便回傳資料的存檔 S->SaveToFile(AOTHER_FILENAME); (2)當 Delimiter 不是 '#', 而是 '#&#' 的狀態下, TStrings 的做法較具彈性.
shieh2700
高階會員


發表:0
回覆:127
積分:100
註冊:2002-06-13

發送簡訊給我
#11 引用回覆 回覆 發表時間:2004-12-10 15:20:57 IP:211.76.xxx.xxx 未訂閱
引言:
引言: 如果是...
procedure TForm1.Button3Click(Sender: TObject);
var
  sl : TStrings ;
  s, sRet : string ;
  i : integer ;
  dw : DWORD ;
begin
  s:='#1111#22#333#4444#55555#6#7#88###ABCD' ;
  Memo1.clear ;
  dw:=GetTickCount ;

  sl:=Split(s,'#');
  try
    if Assigned(sl) then
      if s1.Count > 0 then
        for i:=0 to 99999 do
          sRet:=sl[i mod sl.count];
  finally
    FreeAndNil(sl);
  end ;      Memo1.Lines.Add(format('Time=%d',[GetTickCount-dw])) ;
end;     
我覺得shieh2700做法依舊可取的,見仁見智.    
改成這樣當然 TStrings 會比較快, 因為省去了重新 Parsing 的時間, 就直接索引到需要的資料. 但是在實際運用時, 會呼叫 Parsing 一般都是用來讀入一個大的文字檔, 例如 .CSV檔, 再取出資料處理. 那麼 TStrings 就必需不斷的重新 Create / Free. ...Aquarius
假若是讀取 .CSV 之類的檔案, 我個人的習慣也還是使用 TStrings 來處理, 且不需重新 Create/Free:
procedure CsvToDB( f: string );
const
  d: string =','; //Delimiter
var
  r,s:TStrings;
  i:integer;
begin
  if FileExists(f) then begin
    r := TStringList.Create;
    try
      r.LoadFromFile(f);
      s := TStringList.Create();
      try
        if r.Count>0 then begin
          for i := 0 to r.Count-1 do begin
            s.Text := StringReplace(r[i],d,#13,[rfReplaceAll, rfIgnoreCase])
            //執行要處理的動作...
          end;
        end;
      finally
        FreeAndNil(s);
      end;
    finally
      FreeAndNil(r);
    end;
  end;  
end;
系統時間:2024-05-21 18:35:04
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!