String 如何删除字符周围的空格?

String 如何删除字符周围的空格?,string,delphi,String,Delphi,假设我有以下字符串: s := 'This , is, the Delphi , World!'; 我想要以下输出: Result := 'This,is,the Delphi,World!'; 基本上,我需要一个例程,该例程仅当空格出现在逗号字符(这是我的分隔符)之前或之后时,才会删除所有出现的空格,在其他单词之间保留完整的空格 非常感谢您的帮助 你认为这个解决方案怎么样 function RemoveSpacesAroundDelimiter(var aString:

假设我有以下字符串:

s := 'This , is,       the Delphi  ,    World!';
我想要以下输出:

Result := 'This,is,the Delphi,World!';
基本上,我需要一个例程,该例程仅当空格出现在逗号字符(这是我的分隔符)之前或之后时,才会删除所有出现的空格,在其他单词之间保留完整的空格

非常感谢您的帮助

你认为这个解决方案怎么样

function RemoveSpacesAroundDelimiter(var aString: string; aDelimiter:
    string): string;
begin
  while AnsiContainsText(aString, aDelimiter + ' ') do
    begin
    aString := StringReplace(aString, ', ', aDelimiter, [rfReplaceAll, rfIgnoreCase]);
    end;

  while AnsiContainsText(aString, ' ' + aDelimiter) do
    begin
    aString := StringReplace(aString, ' ' + aDelimiter, aDelimiter, [rfReplaceAll, rfIgnoreCase]);
    end;

  Result := aString;
end;
谢谢
fabio听起来像是TStringList的任务

function UltraTrim(Value: string): string;
var
  sl: TStringList;
  i: Integer;
begin
  sl := TStringList.Create;
  try
    // Prevent the stringlist from using spaces as delimiters too.
    sl.StrictDelimiter := True;

    // Set the comma separated text.
    sl.CommaText := Value;

    // Trim each item.
    for i := 0 to sl.Count -1 do
      sl[i] := Trim(sl[i]);

    // Concat back to comma separated string.
    Result := sl.CommaText;
  finally
    sl.Free;
  end;

end;

又变了一次

  while (pos(', ',s)>0) or (pos(' ,',s)>0) do   begin
    s := StringReplace(s, ', ', ',', [rfReplaceAll]);
    s := StringReplace(s, ' ,', ',', [rfReplaceAll]);   end;

适用于所有Delphi版本。

快速版本可以是:

function RemoveSpacesAroundDelimiter(const aString: string; aDelimiter: char = ','): string;
var S, D, D2: PChar;
begin
  SetLength(result,length(aString));
  if aString<>'' then
  begin
    S := pointer(aString);
    D := pointer(result);
    while S^<>#0 do
    begin
      if S^=' ' then
      begin
        D2 := D;
        repeat
          inc(S);
          D^ := ' ';
          inc(D);
        until S^<>' ';
        if S^=#0 then
          break;
        if S^=aDelimiter then
          D := D2; // trim spaces before comma
      end;
      D^ := S^;
      if (S[0]=aDelimiter) and (S[1]=' ') then
        repeat inc(S) until S^<>' ' else // trim spaces after comma
        inc(S);
      inc(D);
    end;
    SetLength(result,D-pointer(result));
  end;
end;

将字符逐个复制到目标缓冲区中,但要查找空格和分隔符,并记住上次将非空格字符复制到的位置。如果看到一个空格,并且复制的最后一个非空格是分隔符,则跳过该空格。如果它是一个空格,而您复制的最后一个字符不是分隔符,则将其复制到目标,但请记住您添加的最后一个非空格。这样,如果稍后看到分隔符,可以返回并覆盖它

function RemoveSpacesAroundDelimiter(const AString: string; ADelimiter: Char): string;
var
  c: Char;
  dest: Integer;
  LastNonSpace: Integer;
  HaveDelimiter: Boolean;
begin
  Assert(ADelimiter <> ' ');
  SetLength(Result, Length(AString));
  dest := 1;
  LastNonSpace := 0;
  HaveDelimiter := False;
  for c in AString do begin
    if (c = ' ') and HaveDelimiter then
      continue; // Skip this character

    if c = ADelimiter then begin
      dest := LastNonSpace + 1;
      HaveDelimiter := True;
    end else
      HaveDelimiter := False;
    Result[dest] := c;
    if c <> ' ' then
      LastNonSpace := dest;
    Inc(dest);
  end;
  SetLength(Result, dest - 1);
end;
函数RemoveSpacesAroundDelimiter(常量AString:string;ADelimiter:Char):string;
变量
c:半焦;
dest:整数;
LastNonSpace:整数;
分隔符:布尔;
开始
断言(限定符“”);
设置长度(结果、长度(收敛));
目的地:=1;
LastNonSpace:=0;
HaveDelimiter:=False;
对于c,请开始
如果(c='')和分隔符
继续;//跳过此字符
如果c=0,则开始
dest:=LastNonSpace+1;
HaveDelimiter:=True;
结束其他
HaveDelimiter:=False;
结果[dest]:=c;
如果是c,那么
LastNonSpace:=dest;
公司(目的地);
结束;
设置长度(结果,dest-1);
结束;

您可以使用正则表达式。您希望找到前面或后面有任意数量空格的分隔符,并将其全部替换为分隔符的单个副本

function RemoveSpacesAroundDelimiter(const AString: string; const ADelimiter: string): string;
var
  re: TPerlRexEx;
begin
  re := TPerlRegEx.Create;
  try
    re.RegEx := '\s*' + TPerlRegEx.EscapeRegExChars(ADelimiter) + '\s*';
    re.Subject := AString;
    re.Replacement := TPerlRegEx.EscapeRegExChars(ADelimiter);
    re.ReplaceAll;
    Result := re.Subject;
  finally
    re.Free;
  end;
end;
较新的Delphi版本可以使用内置单元。较旧的版本可以使用等效版本


以前发布过演示这一点的文章,但他删除了它,因为他把正则表达式搞错了(删除所有空格,而不仅仅是与分隔符相邻的空格)。

最简单、最简单的方法是使用正则表达式。要解决这样一个简单的问题,最不需要的就是一个庞大复杂的代码块。不幸的是,我现在没有Delphi,我无法测试这段代码,但如果它与此完全不同,那么它非常接近:

s := 'This , is,       the Delphi  ,    World!';
RegEx := TRegEx.Create('[ ]*,[ ]*');
CleanStr := RegEx.Replace(s, ',');

如果您使用的是Delphi XE或更高版本,您可以在一行代码中使用正则表达式轻松地完成这项工作

program regex;

{$APPTYPE CONSOLE}

uses
  RegularExpressions;

const
  Input = 'This , is,       the Delphi  ,    World!';

begin
  Writeln(TRegEx.Replace(Input, ' *, *', ','));
  Readln;
end.

当然,这不是提供的解决方案中运行最快的,但可能这对您来说并不重要。

我认为这是值得添加的,因为它将适用于早期版本的Delphi,而stringlist解决方案(我喜欢)则不适用

我相信它相当快,阅读和理解起来也相当简单

function TForm1.UltraTrim(const InString : String; Delim : Char) : String;
var
  Buf : String;
  i : Integer;
  Token : String;
begin
  Result := '';
  if Trim(InString) <> '' then begin
    i := 1;
    Buf := StringReplace(InString, Delim, #0, [rfReplaceAll]) + #0;
    while i < Length(Buf) do begin
      Token := StrPas(@Buf[i]);
      i := i + Length(Token) + 1;
      Result := Result + Delim + Trim(Token);
    end;
    Result := Copy(Result,2,Length(Result));
  end;
end;
函数TForm1.UltraTrim(const InString:String;Delim:Char):String;
变量
Buf:字符串;
i:整数;
令牌:字符串;
开始
结果:='';
如果修剪(安装)’,则开始
i:=1;
Buf:=StringReplace(InString,Delim,#0,[rfReplaceAll])+#0;
当我
使用绝地密码库,@GolezTrol的答案可以用一行代码重新格式化

function UltraTrim(Value: string): string;
begin
  Result := JclStringList.Split(Value, ',').Trim.Join(',')
end;
使用此功能:

function MBTrim(iStr :string):string;
const CTc= 3{Conditions Count};
      CT :array[0..(CTc-1),0..1]of string= ( (' ,', ','), (', ', ','), ('  ', ' ') );
var   i  :Integer;
begin
  for i := 0 to CTc-1 do while Pos(CT[i,0], iStr) > 0 do
    iStr:= StringReplace(iStr, CT[i,0], CT[i,1], [rfReplaceAll, rfIgnoreCase]);
  Result:= Trim(iStr);
end;
您可以简单地添加其他条件

例如,我添加了
('',)
来转换单词之间的空格,如:

'This , is,       the       Delphi  ,    World!'
我有一个解决方案:

slValores.DelimitedText := StringReplace(sListSummary,' ','',[rfReplaceAll]);

我不知道delphi,但您可以使用逗号作为分隔符拆分字符串,然后对每个生成的子字符串调用Trim(),然后再次组装字符串(可能有一个连接方法可用于字符串列表)哪个版本的delphi?如果您有XE或更高版本,您可以使用正则表达式来执行此操作。我更喜欢使用stringReplace的解决方案,即使所有情况都不受影响。您的解决方案更通用,因为您可以更改分隔符,但我的解决方案更轻。只是一句话:我认为在使用函数时,你不需要把字符串作为函数中的VAR参数传递,除非你想把它用作函数或类似的过程。- 1号,它可以删除所有的空白,并且与<代码>修饰符(<)/代码>相同,但也将删除“Delphi”和“Delphi”之间的空白。@ SasHER,修剪(S)仅删除开头和结尾的空格。如果分隔符前后有多个空格,则不起作用,请参阅我的原始帖子以获得重新访问的版本。@philnext:多个空格如何?可能是最有用的组件除了它不是组件之外,我完全同意。TStringList多次救了我的命。这也删除了字符串开头和结尾的空格。不过,我认为它们不应该被删除,因为它们没有分隔符。@Uwe,这个问题在两个方面与你的说法相矛盾。首先,它要求删除空格“仅当它们出现在逗号字符之前或之后时”。大写和斜体是一个非常严格的要求。其次,法比奥的代码只删除了分隔符旁边的空格。你对“共识”这个词有着奇怪的理解,@Hugh。在我提出这一点之前,我完全看不到关于这是否是法比奥想要的东西的讨论,所以我不确定你们怎么会认为有共识。即使以前有过,现在也没有了。我添加了自己的“快速”答案,但删除了它,因为你的答案更快。小心。此代码假定字符串不包含任何
#0
字符。@文本字符串不应包含任何#0字符,否则将破坏许多Windows API。谁会在这样的Unicode字符串中间放置一个0?@ CasmiPund我喜欢你的版本。这是一个清晰的样本
slValores.DelimitedText := StringReplace(sListSummary,' ','',[rfReplaceAll]);