I am new to Delphi. I was trying to compile a sample code using RAD studio and I get a compiler error saying incompatible types. And i see that, the code is trying to assign a variable of type set of Char
to another variable of type set of Byte
.
Values := ABC.allowedValues;
Here Values
is of type set of Byte
and allowedValues
is of type set of Char
.
I could not find a way to do the above conversion.
Very likely (like "almost certainly"), the best solution is to redesign the code. Something is probably not done in the most appropriate way if you do need to do this.
Also, if you are using a new Delphi version (2009 or newer), Char
is a two-byte Unicode character, and so there is no such thing as a "true" set of Char
, because the base type of a Delphi set must be an ordinal type with at most 256 distinct values. (Two bytes implies 65 536 distinct values.)
Before Delphi 2009, however, Char
was indeed a single-byte character; under the hood it was simply a Byte
. Today, Char = WideChar
while AnsiChar
is the old one-byte character type.
So let us assume that you are either using a pre-Unicode Delphi version or that you are actually working with set of AnsiChar
. If you write set of Char
in a modern Delphi version, the compiler will "helpfully" interpret that as set of AnsiChar
and give you a warning .
A "slow" but truly type-safe approach to performing the conversion is as follows:
type
TCharSet = set of AnsiChar;
TByteSet = set of Byte;
function SetConvert(ACharSet: TCharSet): TByteSet;
begin
Result := [];
for var c in ACharSet do
Include(Result, Ord(c))
end;
This makes use of inline variables introduced in Delphi 10.3 and for..in
loops introduced in Delphi 2005 (?). Pre-10.3, you need to write
function SetConvert(ACharSet: TCharSet): TByteSet;
var
c: AnsiChar;
begin
Result := [];
for c in ACharSet do
Include(Result, Ord(c))
end;
Finally, your question is strictly speaking not well defined, since you don't specify how you want to map character sets into byte sets. Above, I assume that you want to use the mapping induced by the Ord/Chr
mapping between the base types.
Variante A:
uses
System.SysUtils;
type
TCharSet = set of AnsiChar;
TByteSet = set of Byte;
TMySet=packed record
case char of
'A': (a : TCharSet);
'B': (b : TByteSet);
end;
var
x: TMySet;
i: integer;
begin
try
x.a := ['a', 'z', 'A'..'Z'];
for i in x.b do
write(i, ', ');
except
on E: Exception do
Writeln(E.ClassName, ': ', E.Message);
end;
end.
Variante B:
uses
System.SysUtils;
type
TCharSet = set of AnsiChar;
TByteSet = set of Byte;
var
a: TCharSet;
b: TByteSet absolute a;
i: integer;
begin
try
a := ['a', 'z', 'A'..'Z'];
for i in b do
write(i, ', ');
except
on E: Exception do
Writeln(E.ClassName, ': ', E.Message);
end;
end.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.