0

在 php 和 java 中有 explode 和 tokenizer 函数可以将字符串转换为不带标点符号的数组。是函数或delphi中的某种方式来完成这项工作。假设有一个大文件“这是一个带有标点符号、空格和数字 123 的大文件......”我们如何获得数组“这是一个带有标点符号、空格和数字 123 的大文件”

非常感谢您提前。

是的,我们只想要 [0..9],[a..z],[A..Z],就像正则表达式中的 \w。我们可以在 Tperlregex 中使用正则表达式来提取 \w 并将它们放入 Tstringlist 中,就好像 tstringlist 是一个数组一样,但它可能没有那么高效?谢谢你。

4

3 回答 3

4

If you need a function that takes a string and returns an array of strings, these strings being the substrings of the original separated by punctuation, as Eugene suggested in my previous answer, then you can do

type
  StringArray = array of string;
  IntegerArray = array of integer;
  TCharSet = set of char;

function split(const str: string; const delims: TCharSet): StringArray;
var
  SepPos: IntegerArray;
  i: Integer;
begin
  SetLength(SepPos, 1);
  SepPos[0] := 0;
  for i := 1 to length(str) do
    if str[i] in delims then
    begin
      SetLength(SepPos, length(SepPos) + 1);
      SepPos[high(SepPos)] := i;
    end;
  SetLength(SepPos, length(SepPos) + 1);
  SepPos[high(SepPos)] := length(str) + 1;
  SetLength(result, high(SepPos));
  for i := 0 to high(SepPos) -  1 do
    result[i] := Trim(Copy(str, SepPos[i] + 1, SepPos[i+1] - SepPos[i] - 1));
end;

Example:

const
  PUNCT = ['.', ',', ':', ';', '-', '!', '?'];

procedure TForm4.FormCreate(Sender: TObject);
var
  str: string;
begin
  for str in split('this, is, a! test!', PUNCT) do
    ListBox1.Items.Add(str)
end;
于 2010-10-22T14:48:52.650 回答
2

这取决于“字母数字字符”和“标点符号”的定义。

例如,如果我们定义一组标点符号

const
  PUNCT = ['.', ',', ':', ';', '-', '!', '?'];

并考虑所有其他字符字母数字,那么你可以做

function RemovePunctuation(const Str: string): string;
var
  ActualLength: integer;
  i: Integer;
const
  PUNCT = ['.', ',', ':', ';', '-', '!', '?'];
begin
  SetLength(result, length(Str));
  ActualLength := 0;
  for i := 1 to length(Str) do
    if not (Str[i] in PUNCT) then
    begin
      inc(ActualLength);
      result[ActualLength] := Str[i];
    end;
  SetLength(result, ActualLength);
end;

此函数将字符串转换为字符串。如果您想将字符串转换为字符数组,只需执行

type
  CharArray = array of char;

function RemovePunctuation(const Str: string): CharArray;
var
  ActualLength: integer;
  i: Integer;
const
  PUNCT = ['.', ',', ':', ';', '-', '!', '?'];
begin
  SetLength(result, length(Str));
  ActualLength := 0;
  for i := 1 to length(Str) do
    if not (Str[i] in PUNCT) then
    begin
      result[ActualLength] := Str[i];
      inc(ActualLength);
    end;
  SetLength(result, ActualLength);
end;

(是的,在 Delphi 中,字符串使用基于 1 的索引,而数组使用基于 0 的索引。这是出于历史原因。)

于 2010-10-22T14:35:16.460 回答
0

似乎没有像 Java 标记器那样的内置功能。很久以前,我们编写了一个类似于 Java 的分词器类,它成为 ElPack 组件套件(现在的 LMD ElPack)的一部分。这是一些类似于 Java的字符串标记器的实现(刚刚在 Google 中找到了这个链接,所以我无法评论代码质量)。

于 2010-10-22T14:46:26.800 回答