急! 帮忙翻译一个简单C函数为delphi(300)

小伶

New Member
Member
#1
int getmystr(char *s, char *dl, char *gg[], int len){ int n = 1;
gg [0] = s;
while (*s != '/0') { if ((strchr(dl, (int) *s) != NULL) && n < len) {/* extern char *strchr(char *s,char c);
查找字符串s中首次出现字符c的位置 返回首次出现c的位置的指针,如果s中不存在c则返回NULL。 /n 回车换行 /r 回车 /0 结尾*/ *s = '/0';
while (*(s + 1) != '/0' && strchr (dl, (int) *(s + 1)) != NULL) s++;
gg[n++] = s + 1;
} if (*s == '/n' || *s == '/r') { *s = '/0';
break;
} s++;
} if (n < len) gg[n] = NULL;
return (n);}
 

luoyanqing119

New Member
Member
#3
改改数据结构中类型的申明,逻辑控制改一下就可以了。-----------无论是条件和循环,常用的这几种语言都有对应的控制方式
 

wql

New Member
Member
#4
function getmystr(s:string;dl:char;gg:pchar;len:integer):integer;var n:integer;
begin
n:= 1;
while (s<>'')do
brgin if ((strchr(dl, (int) *s) != NULL) and n<len) then
/* extern char *strchr(char *s,char c);
查找字符串s中首次出现字符c的位置 返回首次出现c的位置的指针,如果s中不存在c则返回NULL。 /n 回车换行 /r 回车 /0 结尾*/ delete(s,1,1);
while (s<>'' and strchr (dl, (int) *(s + 1)) != NULL)do
delete(s,1,1);
inc(n);
end;
if (s[1] = #13 or s[1] = #10) then
begin
delete(s,1,1);
break;
end;
delete(s,1,1);
end;
result:=n;
end;
 

hanyuhen1

New Member
Member
#5
设 s := '爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me';
dl := ',';那么执行后gg[0] := '爷爷';gg[1] := '奶奶';gg[2] := '爸爸';gg[3] := '妈妈';gg[4] := 'me';没看出来那段C语言能实现这个效果;我觉得只能是这样设 s := 'a,,bb,,,,,,,cc,,,dd,,,me';gg[0] := a;gg[1] := b;gg[2] := c;gg[3] := d;gg[4] := m;
 

轻舞肥羊

New Member
Member
#8
delphi有现成的函数,也没内存问题,为啥不用呢procedure TForm1.Button4Click(Sender: TObject);var s : string;
gg : array of string;
lst : TStrings;
i : Integer;
begin
s := '爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me';
lst := TStringList.Create;
try ExtractStrings([','], [], PChar(s), lst);
SetLength(gg, lst.Count);
for i := 0 to lst.Count - 1do
gg := lst;
finally lst.Free;
end;
for i := 0 to High(gg)do
memo1.Lines.Add(gg);
end;
 

关门放狗

New Member
Member
#9
function getmystr(s:pChar;dl:pChar;
arrText: array of pchar;len:Integer):Integer;var n:Word;
begin
arrText[0]:=s;
while (Integer(s^)<>0)do
begin
// if ((strchr(dl, (int) *s) != NULL) && n < len) { if (Pos(string(s^),StrPas(dl))>0) and (n<len) then
begin
s^:=#0;
while ((s+1)^<>'0') and (Pos(string((s+1)^),StrPas(dl))>0)do
Inc(s);
inc(n);
arrText[n]:=s+1;
end;
if (s^=#13) and (s^=#10) then
begin
s^:=#0;
exit;
end;
end;
end;
没给出具体调用不好调试 ,这个有问题哦
 

wangdonghai

New Member
Member
#10
//下面的代码只处理分隔符为一个字符的情况procedure GetMyStr(s:pChar;dl:char);var c:array[0..255] of char;
p:pChar;
i1,i2:Integer;
begin
p:=s;
i1:=0;
i2:=0;
while p^<>#0do
begin
if p^=dl then
begin
if i2-i1>1 then
begin
StrLCopy(c,s+i1,i2-i1);
showmessage(c);
end;
i1:=i2+1;
end;
inc(p);
inc(i2);
end;
if i1<i2 then
//末尾没有分隔符 begin
StrLCopy(c,s+i1,i2-i1);
showmessage(c);
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
GetMyStr(PChar('爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me'),',');
end;
 

小伶

New Member
Member
#11
谢谢各位的回复 谢谢wql函数看起来简单 实际有点复杂.结果是为了分割出非空的与分割符dl不相同的字符串, 然后存放在gg数组中.设 s := '爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me';
dl := ',';那么执行后gg[0] := '爷爷';gg[1] := '奶奶';gg[2] := '爸爸';gg[3] := '妈妈';gg[4] := 'me';我自己写了一个, 实现了这个结果, 但是感觉不是最好的翻译.因为整个C函数关键之关键在一句 *s = '/0';
由于delphi的指针运用没C那么灵活, 所以, 直译不成, 我只好意译了.function GetMyStr(s, dl: string;
var gg: Array of string;
Len: Integer) : Integer;var i, n, l: Integer;
str: string;
begin
for i := Low(gg) to High(gg)do
gg := '';
n := 0;
l := length(s);
str := '';
for i:=1 to ldo
begin
if s <> dl then
begin
str := str + s;
if (i <= Len) then
// and ((i + 1) < l) if (length(str) > 0) and ((i = l) or (i = Len) or (s[i + 1] = dl)) then
begin
gg[n] := str;
inc(n);
str := '';
end;
end;
end;
Result := n + 1;
// + 1 是为了跟C代码一致end;
哪位朋友能原汁原味的把这个C函数翻译出来马上结帖.要求: 1.用指针.2.string不要, 要用pchar. 因为这个函数要被很多个函数调用到, 我改为string是不得以之举.
 

wangdonghai

New Member
Member
#12
//修改前的函数不能处理 '爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me,.'//需要修改procedure GetMyStr(s:pChar;dl:char);var c:array[0..255] of char;
p:pChar;
i1,i2:Integer;
begin
p:=s;
i1:=0;
i2:=0;
while p^<>#0do
begin
if (p^=dl) then
begin
if (i2-i1<>0) and ((s+i1)<>dl) then
begin
StrLCopy(c,s+i1,i2-i1);
showmessage(c);
end;
i1:=i2+1;
end;
inc(p);
inc(i2);
end;
if i1<i2 then
//末尾没有分隔符 begin
StrLCopy(c,s+i1,i2-i1);
showmessage(c);
end;
end;
 

小伶

New Member
Member
#13
谢谢 wangdonghaiprocedure GetMyStr4(s: PChar;
dl: char);var c: array[0..255] of char;
p: PChar;
i1, i2: Integer;
begin
p := s;
i1 := 0;
i2 := 0;
while p^ <> #0do
begin
if (p^ = dl) then
begin
if (i2 - i1 <> 0) and ((s + i1) <> dl) then
begin
StrLCopy(c, s + i1, i2 - i1);
Form1.Memo1.Lines.Add(c);
end;
i1 := i2 + 1;
end;
inc(p);
inc(i2);
end;
if i1 < i2 then
//末尾没有分隔符 begin
StrLCopy(c, s + i1, i2 - i1);
Form1.Memo1.Lines.Add(c);
end;
end;
procedure TForm1.Button18Click(Sender: TObject);
begin
GetMyStr4('爷999,,奶奶88,,,,,,,爸爸,,,妈妈,,,me', ',');
end;
============================================我自己试了轻舞肥羊的办法 把 ExtractStrings 封装进来 但是s只能用string了, 速度和算法还是不够理想.function getmystr3(s : string;
dl: PChar;
var gg: array of string;
len: Integer): Integer;var lst: TStrings;
i: Integer;
s1: string;
begin
Result := 0;
for i := Low(gg) to High(gg)do
gg := '';
if len > length(s) then
exit;
s1 := copy(s, 1, len);
lst := TStringList.Create;
try ExtractStrings([dl^], [], PChar(s1), lst);
//SetLength(gg, lst.Count);
// High(gg) for i := 0 to lst.Count - 1do
gg := lst;
Result := lst.Count;
finally lst.Free;
end;
end;
procedure TForm1.Button16Click(Sender: TObject);var n, i, j: Integer;
gg: Array[0..8] of string;// [0..19]begin
n := getmystr3('爷999,,奶奶88,,,,,,,爸爸,,,妈妈,,,me', ',', gg, 33);
for i := 0 to High(gg)do
Form1.Memo1.Lines.Add(gg);
Memo1.Lines.Add(format('一共分割几个: n = %d', [n]));
end;
 

小伶

New Member
Member
#14
谢谢 轻舞肥羊, ExtractStrings让我见识到Borland公司的程序员写代码是多么厉害, 对比我和他的翻译, 真是天壤之别.谢谢 关门放狗, 我要的就是这种风格的翻译.但是您翻译的这个函数试验了一下是死循环.谢谢 wangdonghai 您的翻译也是另一种不错的思路.整理如下:// Borland公司的程序员:function ExtractStrings(Separators, WhiteSpace: TSysCharSet;
Content: PChar;
Strings: TStrings): Integer;var Head, Tail: PChar;
EOS, InQuote: Boolean;
QuoteChar: Char;
Item: string;
begin
Result := 0;
if (Content = nil) or (Content^=#0) or (Strings = nil) then
Exit;
Tail := Content;
InQuote := False;
QuoteChar := #0;
Strings.begin
Update;
try repeat while Tail^ in WhiteSpace + [#13, #10]do
Tail := StrNextChar(Tail);
Head := Tail;
while Truedo
begin
while (InQuote and not (Tail^ in [QuoteChar, #0])) or not (Tail^ in Separators + [#0, #13, #10, '''', '"'])do
Tail := StrNextChar(Tail);
if Tail^ in ['''', '"'] then
begin
if (QuoteChar <> #0) and (QuoteChar = Tail^) then
QuoteChar := #0 else
if QuoteChar = #0 then
QuoteChar := Tail^;
InQuote := QuoteChar <> #0;
Tail := StrNextChar(Tail);
end else
Break;
end;
EOS := Tail^ = #0;
if (Head <> Tail) and (Head^ <> #0) then
begin
if Strings <> nil then
begin
SetString(Item, Head, Tail - Head);
Strings.Add(Item);
end;
Inc(Result);
end;
Tail := StrNextChar(Tail);
until EOS;
finally Strings.EndUpdate;
end;
end;
procedure TForm1.Button12Click(Sender: TObject);var s : string;
gg : array of string;
lst : TStrings;
i : Integer;
begin
s := '爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me';
lst := TStringList.Create;
try ExtractStrings([','], [], PChar(s), lst);
SetLength(gg, lst.Count);
for i := 0 to lst.Count - 1do
gg := lst;
finally lst.Free;
end;
for i := 0 to High(gg)do
memo1.Lines.Add(gg);
end;
function getmystr(s: PChar;
dl: PChar;
arrText: array of pchar;
len: Integer): Integer;var n: Word;
begin
arrText[0] := s;
while (Integer(s^) <> 0)do
begin
// if ((strchr(dl, (int) *s) != NULL) && n < len) { if (Pos(string(s^), StrPas(dl)) > 0) and (n < len) then
begin
s^ := #0;
while ((s + 1)^ <> '0') and (Pos(string((s + 1)^), StrPas(dl)) > 0)do
Inc(s);
inc(n);
arrText[n] := s + 1;
end;
if (s^ = #13) and (s^ = #10) then
begin
s^ := #0;
exit;
end;
end;
end;
procedure TForm1.Button13Click(Sender: TObject);var n, i, j: Integer;
dl: Array [0..15] of pchar;// [0..19]begin
n := getmystr('爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me', ',', dl, 20);
Memo1.Lines.Add(format('n = %d %s %s %s %s ', [n, dl[0], dl[1], dl[2], dl[3]]));
end;
//下面的代码只处理分隔符为一个字符的情况procedure GetMyStr2(s: PChar;
dl: char);var c: array[0..255] of char;
p: PChar;
i1, i2: Integer;
begin
p := s;
i1 := 0;
i2 := 0;
while p^ <> #0do
begin
if p^ = dl then
begin
if i2 - i1 > 1 then
begin
StrLCopy(c, s + i1, i2 - i1);
showmessage(c);
end;
i1 := i2 + 1;
end;
inc(p);
inc(i2);
end;
if i1 < i2 then
//末尾没有分隔符 begin
StrLCopy(c, s + i1, i2 - i1);
showmessage(c);
end;
end;
procedure TForm1.Button14Click(Sender: TObject);
begin
GetMyStr2(PChar('爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me'),',');
end;
我还想看看各位处理字符串的高手还要没有其他更理想的翻译, 再等一两天再结贴吧.谢谢您们!
 
#16
var Form1: TForm1;
dl: array of WideString;
// [0..19]function getmystr(s: PWideChar;
dl: PWideChar;
var arrText: array of WideString;
len: Integer): Integer;var n: Integer;
tmp: PWideChar;
dlstr:string;
begin
n := 0;
tmp := s;
if (s^ <> #0) then
begin
dlstr:= WideCharToString(dl);
while ((s + 1)^ <> #0) and (Pos(dlstr, s + 1) > 0)do
begin
if Trim(Copy(s, 0, Pos(dlstr, s) - 1)) <> '' then
begin
arrText[n] := Copy(s, 0, Pos(dlstr, s) - 1);
n := n + 1;
end;
s := s + Pos(dlstr, s);
end;
if ((Pos(dlstr, s + 1) = 0) and ((s + 1)^ <> #0)) then
arrText[n] := RightStr(tmp, Length(WideCharToString(tmp)) - LastDelimiter(dlstr, WideCharToString(tmp)));
result := n + 1;
end else
result := n// if n < len then
arrText[n] := '';
end;
procedure TForm1.Button1Click(Sender: TObject);var i: Integer;
begin
SetLength(dl, 15);
// i := getmystr('爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me,goudan,123', ',', dl, 20);
i := getmystr('爷爷, ,奶奶,,', ' ', dl, 20);
Memo1.Lines.Add(format('n = %d, %s', [i, dl[0]]));
// Memo1.Lines.Add(format('n = %d, %s, %s, %s, %s ', [i, dl[0], dl[1], dl[2], dl[3]]));
end;
 

小伶

New Member
Member
#17
function getmystr6(s: PWideChar;
dl: PWideChar;
var arrText: array of WideString;
len: Integer): Integer;var n: Integer;
tmp: PWideChar;
dlstr: string;
begin
n := 0;
tmp := s;
if (s^ <> #0) then
begin
dlstr := WideCharToString(dl);
while ((s + 1)^ <> #0) and (Pos(dlstr, s + 1) > 0)do
begin
if Trim(Copy(s, 0, Pos(dlstr, s) - 1)) <> '' then
begin
arrText[n] := Copy(s, 0, Pos(dlstr, s) - 1);
n := n + 1;
end;
s := s + Pos(dlstr, s);
end;
if ((Pos(dlstr, s + 1) = 0) and ((s + 1)^ <> #0)) then
arrText[n] := RightStr(tmp, Length(WideCharToString(tmp)) - LastDelimiter(dlstr, WideCharToString(tmp)));
result := n + 1;
end else
result := n // if n < len then
arrText[n] := '';
end;
procedure TForm1.Button20Click(Sender: TObject);var i, n: Integer;
gg: array of WideString;
// [0..19]begin
SetLength(gg, 7);
n := getmystr6('爷爷,,奶奶,,,,,,,爸爸,,,妈妈,,,me,goudan,123', ',', gg, 44);
for i := 0 to High(gg)do
Form1.Memo1.Lines.Add(gg);
Memo1.Lines.Add(format('n = %d', [n]));
end;
十分感谢 关门放狗sizeof(PChar) = 4sizeof(PAnsiChar) = 4sizeof(PWideChar) = 4PChar指向null结束的Char字符串的指针,类似于C的char*或lpstr类型。 PAnsiChar指向null结束的AnsiChar字符串的指针。 PWideChar指向null结束的WideChar字符串的指针。在C语言的 char *, 翻译为delphi, PChar, PAnsiChar, PWideChar的字节都相同, 究竟哪种比较好呢? 用PWideChar是否有什么考虑?
 
#18
D7是ANSICHAR 2009是UNICODE D7中的很多函数是基于ANSICHAR 对UNICODE会有问题 所以转换了一下。 说实话我对内存理解的还很不到位,只是有个模糊的概念,内部具体是什么,怎么布局还是一脑袋浆糊。