我编写了一个 Pascal 函数来替换文件中的整行或其中的一部分,以便在 Inno Setup 中使用:
function ReplaceInFile(const FilePath, OldLinePart, Replacement: String;
DoReplaceWholeLine, IsCaseSensitive: Boolean): Boolean;
var
FileLines: TArrayOfString;
Index: Integer;
FoundAtPos: Integer;
LeftOfOldLinePart: String;
RightOfOldLinePart: String;
IsReplaced: Boolean;
begin
Result := False;
if FileExists(FilePath) then begin
LoadStringsFromFile(FilePath, FileLines);
for Index := 0 to GetArrayLength(FileLines) - 1 do
begin
repeat
FoundAtPos := 0;
if IsCaseSensitive then
FoundAtPos := Pos(OldLinePart, FileLines[Index])
else
FoundAtPos := Pos(Uppercase(OldLinePart), Uppercase(FileLines[Index]));
if FoundAtPos > 0 then begin
if DoReplaceWholeLine then begin
FileLines[Index] := Replacement;
IsReplaced := True;
end
else begin
LeftOfOldLinePart := Copy(FileLines[Index], 1, FoundAtPos - 1);
RightOfOldLinePart := Copy(FileLines[Index], FoundAtPos
+ Length(OldLinePart), Length(FileLines[Index])
- Length(LeftOfOldLinePart + OldLinePart));
FileLines[Index] := LeftOfOldLinePart + Replacement + RightOfOldLinePart;
IsReplaced := True;
end;
end;
until FoundAtPos = 0;
end;
if IsReplaced then
if SaveStringsToFile(FilePath, FileLines, False) then
Result := True;
end;
end;
它过去工作得很好,但只用替换文件替换了 FilePath 指定的文件的每一行上第一次出现的 OldLinePart。那是我添加重复循环的时候。逻辑是Pos()
当没有找到更多的事件时返回 0。然后它应该继续下一行。然而,事实是,循环一直在无限循环,我不知道为什么。我尝试在of 子句中添加一个Break
语句,但没有运气......else
if FoundAtPos > 0
编辑:显然已经很晚了。我用一个很长的字符串替换了 OldLinePart ......其中包含相同的单词。
该问题已解决如下。
function ReplaceInFile(const FilePath, OldLinePart, Replacement: String; DoReplaceWholeLine, IsCaseSensitive: Boolean): Boolean;
var
FileLines: TArrayOfString;
Index: Integer;
SearchLinePart: String;
FoundAtPosition: Integer;
SearchOffset: Integer;
LeftOfOldLinePart: String;
RightOfOldLinePart: String;
IsReplaced: Boolean;
begin
Result := False;
if FileExists(FilePath) then
begin
LoadStringsFromFile(FilePath, FileLines);
for Index := 0 to GetArrayLength(FileLines) - 1 do
begin
SearchOffset := 0;
SearchLinePart := FileLines[Index];
repeat
FoundAtPosition := 0;
if IsCaseSensitive then
FoundAtPosition := SearchOffset + Pos(OldLinePart, SearchLinePart)
else
FoundAtPosition := SearchOffset + Pos(Uppercase(OldLinePart), Uppercase(SearchLinePart));
if FoundAtPosition > SearchOffset then
begin
if DoReplaceWholeLine then
begin
FileLines[Index] := Replacement;
IsReplaced := True;
Break;
end
else
begin
LeftOfOldLinePart := '';
RightOfOldLinePart := '';
LeftOfOldLinePart := Copy(FileLines[Index], 1, FoundAtPosition - 1);
RightOfOldLinePart := Copy(FileLines[Index], FoundAtPosition + Length(OldLinePart), Length(FileLines[Index]) - Length(LeftOfOldLinePart + OldLinePart));
FileLines[Index] := LeftOfOldLinePart + Replacement + RightOfOldLinePart;
IsReplaced := True;
SearchOffset := Length(LeftOfOldLinePart + Replacement);
SearchLinePart := RightOfOldLinePart;
end;
end;
until FoundAtPosition <= SearchOffset;
end;
if IsReplaced then
if SaveStringsToFile(FilePath, FileLines, False) then
Result := True;
end;
end;