2

I am developing a project with Delphi and I want to convert the byte array to string type. How can I do?

Example C# codes:

private void ListenerOnDataTransmit(DataTransmitEventArgs e)
{
    transmittedMsg = BitConverter.ToString(e.TransmittedBytes, 0, e.TransmittedBytes.Length);
    try { Invoke(new EventHandler(UpdateTransmittedMessagesListView)); }
    catch { }
}
1
  • 2
    You forgot to tell us what you mean by "converting byte array to string". There are several different interpretations, all reasonable: (1) treat the byte array as ASCII and obtain the text it encodes; (2) treat the byte array as UTF8 and obtain the text it encodes; (3) obtain a raw hexadecimal data representation of the array; (4) obtain a raw binary data representation of the array; etc. In the latter cases, do you want to group the digits? Commented Nov 23, 2020 at 20:36

2 Answers 2

3

The BitConverter.ToString() method "Converts the numeric value of each element of a specified array of bytes to its equivalent hexadecimal string representation." You can do the same thing manually in Delphi 7 by using the SysUtils.IntToHex() function in a loop, eg:

uses
  ..., SysUtils;

var
  bytes: array of byte;
  s: string;
  i: Integer;
begin
  bytes := ...;
  s := '';
  if bytes <> nil then
  begin
    s := IntToHex(bytes[0], 2);
    for i := 1 to High(bytes) do
      s := s + '-' + IntToHex(bytes[i], 2);
  end;
end;
Sign up to request clarification or add additional context in comments.

5 Comments

Perfectly valid, but (very) inefficient for long buffers due to the constant reallocation of the string.
@AndreasRejbrand Yes, there are many different ways to approach this. Above is just one example.
True. And for small buffers it is certainly good enough, so +1.
At least now we got a really good Q&A that we can use as a canonical one to close duplicates against.
@RemyLebeau Thanks, i was looking for this.
3

I suspect you want a function that takes an array of bytes (or a raw pointer to bytes) and returns a string containing the data in hexadecimal form.

I always use the following routine of mine to do this:

function BytesToString(ABuf: PByte; ALen: Cardinal): string; overload;
const
  HexDigits: array[0..$F] of Char = '0123456789ABCDEF';
var
   i: Integer;
begin
   if ALen = 0 then
   begin
     Result := '';
     Exit;
   end;
   SetLength(Result, 3 * ALen - 1);
   Result[1] := HexDigits[ABuf^ shr 4];
   Result[2] := HexDigits[ABuf^ and $0F];
   for i := 1 to ALen - 1 do
   begin
     Inc(ABuf);
     Result[3*i + 0] := ' ';
     Result[3*i + 1] := HexDigits[ABuf^ shr 4];
     Result[3*i + 2] := HexDigits[ABuf^ and $0F];
   end;
end;

type
  TByteArray = array of Byte;

function BytesToString(ABytes: TByteArray): string; overload;
begin
  Result := BytesToString(PByte(ABytes), Length(ABytes));
end;

The first overload takes a raw pointer and a length, while the second overload takes a dynamic array of bytes.

This is a very fast implementation, since I do not use string concatenation (which requires constant heap reallocations).


The above code was written specifically for the old Delphi 7 compiler and RTL. A modern version would look more like this:

function BytesToString(ABuf: PByte; ALen: Cardinal): string; overload;
const
  HexDigits: array[0..$F] of Char = '0123456789ABCDEF';
var
   i: Integer;
begin
   if ALen = 0 then
    Exit('');
   SetLength(Result, 3 * ALen - 1);
   Result[1] := HexDigits[ABuf[0] shr 4];
   Result[2] := HexDigits[ABuf[0] and $0F];
   for i := 1 to ALen - 1 do
   begin
     Result[3*i + 0] := ' ';
     Result[3*i + 1] := HexDigits[ABuf[i] shr 4];
     Result[3*i + 2] := HexDigits[ABuf[i] and $0F];
   end;
end;

function BytesToString(ABytes: TArray<Byte>): string; overload;
begin
  Result := BytesToString(PByte(ABytes), Length(ABytes));
end;

The above code groups each byte using a space character. Of course, you might not want that, but doing it without grouping is a simpler task, so I'll leave that as an exercise.

2 Comments

To be honest, I was really scratching my head when I saw the 3 * ALen... That is, until I saw the space.
IIRC, PByte-based ptr math isn't available in Delphi 7, so I replaced it with some more old-school methods.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.