Mega Code Archive

 
Categories / Delphi / Examples
 

Textmanip

VARIOUS TEXT MANIPULATION ROUTINES INCLUDING STRING COMPARISON ASSIGNMENT To copy from PChar to PChar, or from PChar to array, use StrCopy... ***************************VARIOUS********************************* var userWordPC, dictWordPC: PChar; dictWord: String thisWord: String; thisChunk: array [1..30] of Char; fileNameArray: array[0..13] of Char; fileNameString: String; begin userWordPC := 'tree'; dictWordPC := PChar(dictWord); thisWord := String(thisChunk); {next one copies a Delphi-style PChar string into a character array} fileNameArray := StrPCopy(CWForm.SaveDialog.Filename); {and to copy a character array INTO a string, we just use a typecast:} fileNameString := String(fileNameArray); {and to copy a normal string (of String type) into a character array we must explicitly copy characters one at a time, like this:} var stringLength, i: Integer; longFileName: String; tempArray: array[0..100] of Char; begin stringLength := Length(longFileName); for i := 1 to stringLength do begin tempArray[i - 1] := longFilename[i]; end; end; ******************************************************************************************* SPLIT STRING BY DELIMITER Hi Here is a generic 'SplitStringByDelimiter' routine which might be useful (if only for filing away) Richard procedure TMainForm.FormCreate(Sender: TObject); var lines: TStringList; ballOfString: String; returnValue: Integer; tempString: String; begin lines := TStringList.Create; ballOfString := 'this is a ball of string, useful for finding your way, in a dark cave, if you had the foresight to trail it, behind you on the way in'; returnValue := SplitStringByDelimiter(ballOfString, lines, ','); if (returnValue = -1) then begin tempString := 'Problems were encountered when trying to split long strings'; Application.MessageBox(PChar(tempString), ' String Handling Error', mb_OK); end; lines.Free; end; ////////////////////////////////////////////////////////////////////////////////////////// function TMainForm.SplitStringByDelimiter(longString: String; var subStrings: TStringList; delimiter: Char): Integer; const MaxStrLength = 4096; var subStrStart: Integer; idx: Integer; lenStr: Integer; tempArray: array[0..MaxStrLength] of Char; tempString: String; begin lenStr := Length(longString); if (lenStr >= MaxStrLength) then begin Result := -1; exit; end; for idx := 1 to lenStr do begin tempArray[idx - 1] := longString[idx]; end; tempArray[idx] := #0; subStrStart := 0; for idx := 0 to lenStr do begin if (tempArray[idx] = delimiter) then begin tempString := Copy(tempArray, subStrStart, (idx - subStrStart)); subStrings.Add(tempString); end; end; end; //////////////////////////////////////////////// -------------------------------------------- ************************************************************************************* COMPARISON {WHERE compResult is an Integer, and userWordPC and dictWordPC are PChars} compResult := StrComp(userWordPC,dictWordPC); if (compResult = 0) then procedure TForm1.TempFindMatch(dictWord: String); {check dictionary word against user word and see if they match string comparison routines can be a little unpredictable in Delphi -you SHOULD be able to say if StrOne = StrTwo then ... (where both StrOne and StrTwo are String types that is) but sometimes that works and sometimes it doesn't. Converting string to PChar types and using StrComp() DOES work though} var userWordPC,dictWordPC: PChar; compResult: Integer; begin userWordPC := 'tree'; dictWordPC := PChar(dictWord); compResult := StrComp(userWordPC,dictWordPC); if (compResult = 0) then begin ShowMessage('match found for tree'); end; end; procedure TForm1.CapitalButtonClick(Sender: TObject); {gubbins code... NOTE ye have te be REALLY careful with PChar variables...} {-the 'memo' type is one such. PChars are pointers to characters, so many of} {the normal low-level string-handling routines (like substituting each instance} {of a particular character for another, for instance) are potentially dangerous} {if you screw up with the syntax (which is easily done, as the compiler may} {well let you get away with it. Best strategy is to 1) convert your PChar} {variable to a string (using a simple assignment), 2) perform what operations} {you must on the string variable, 3) overwrite the old PChar variable with the} {new string (using a simple assignment statement again)...} var TotalLines : Integer; LineLength : Integer; x, y, LeftPos, RightPos : Integer; TempString : String; begin TotalLines := Memo1.Lines.Count; for x := 0 to TotalLines do begin LineLength := Length(Memo1.Lines[x]); TempString := Memo1.Lines[x]; y := 0; while (y < LineLength) do begin Inc(y); if (y >= LineLength) then break; if (TempString[y] = '<') then begin Inc(y); repeat TempString[y] := UpCase(TempString[y]); Inc(y); until ((y >= LineLength) or (TempString[y] = '>')); end; {end if} end; {end while} Memo1.Lines[x] := TempString; TempString := ''; end; end; function TForm1.GetWordsEnd: Integer; var len: Integer; textEnd: Boolean; begin len := 1; textEnd := False; while ((textEnd = False) and (len < bufSize)) do begin if (((dictBuf[len] >= 'A') and (dictBuf[len] <= 'Z')) or ((dictBuf[len] >= 'a') and (dictBuf[len] <= 'z')) or (dictBuf[len] = ',' )) then begin Inc(len); end else begin textEnd := True; end; end; Result := len; end; procedure TForm1.ExtractWords; {parse out one word at a time from the (comma-delimited) text file... this procedure also involves some 'low-level' stuff -it's necessary to work chunks of text in the form of a 'null-terminated string' in the form of a character array, and then convert that to Delphi's kind of string...} var i,pos,x,y: Integer; charsLen: Integer; thisChunk: array [1..30] of Char; thisWord: String; begin i := 1; pos := 1; for x := 1 to 30 do begin thisChunk[x] := #0; end; charsLen := GetWordsEnd; while (i < charsLen) do begin while ((not(dictBuf[i] = ',') and (i < charsLen))) do begin Inc(i); end; y := 1; for x := pos to (i - 1) do begin thisChunk[y] := dictBuf[x]; Inc(y); end; {use a typecast to convert from character array to string...} thisWord := string(thisChunk); TempFindMatch(thisWord); {skip a comma by incrementing i...} Inc(i); pos := i; for x := 1 to 30 do begin thisChunk[x] := #0; end; end; {outer while} end; ***************************************************************** {reverse a sequence of characters...} patt is a string tempArray is an array j := (pattLen - 1); for i := 1 to pattLen do begin tempArray[j] := patt[i]; Dec(j); end;