Изменение имен атрибутов при сериализации в XML в Delphi
При работе с сериализацией объектов в XML формат в Delphi, важно уметь контролировать и оптимизировать размеры создаваемых файлов. Одним из способов уменьшения объема данных является использование атрибутов для сокращения имен свойств. В данном случае, рассмотрим, как изменить имя атрибута для свойства при сериализации, если оно помечено специальным атрибутом.
Описание проблемы
Рассмотрим класс MyClass, который наследуется от TPersistent и имеет опубликованное свойство ClassCaption, помеченное атрибутом MyAttr с именем "Class". При сериализации в XML используется следующий алгоритм:
lPropCount := GetPropList(PTypeInfo(Obj.ClassInfo), lPropList);
for i := 0 to lPropCount - 1 do begin
lPropInfo := lPropList^[i];
lPropName := string(lPropInfo^.Name);
if IsPublishedProp(Obj, lPropName) then begin
ItemNode := RootNode.AddChild(lPropName);
ItemNode.NodeValue := VarToStr(GetPropValue(Obj, lPropName, False));
end;
end;
Требуется добавить условие, которое позволит, если свойство помечено атрибутом MyAttr, получать значение "MyAttr.Name" вместо "lPropInfo^.Name".
Подтвержденный ответ
Для решения задачи можно использовать следующую функцию, которая возвращает имя атрибута, если свойство помечено атрибутом MyAttr:
uses
SysUtils,
Rtti,
TypInfo;
function GetPropAttribValue(ATypeInfo: Pointer; const PropName: string): string;
var
ctx: TRttiContext;
typ: TRttiType;
Aprop: TRttiProperty;
attr: TCustomAttribute;
begin
Result := '';
ctx := TRttiContext.Create;
typ := ctx.GetType(ATypeInfo);
for Aprop in typ.GetProperties do
begin
if (Aprop.Visibility = mvPublished) and (SameText(PropName, Aprop.Name)) then
begin
for attr in AProp.GetAttributes do
begin
if attr is MyAttr then
begin
Result := MyAttr(attr).Name;
Exit;
end;
end;
Break;
end;
end;
end;
Если функция возвращает пустую строку, это означает, что свойство не помечено атрибутом MyAttr, и тогда следует использовать значение "lPropInfo^.Name".
Пример использования
lPropCount := GetPropList(PTypeInfo(Obj.ClassInfo), lPropList);
for i := 0 to lPropCount - 1 do begin
lPropInfo := lPropList^[i];
sAttrName := GetPropAttribValue(PTypeInfo(Obj.ClassInfo), string(lPropInfo^.Name));
if sAttrName = '' then
ItemNode := RootNode.AddChild(string(lPropInfo^.Name))
else
ItemNode := RootNode.AddChild(sAttrName);
ItemNode.NodeValue := VarToStr(GetPropValue(Obj, lPropName, sAttrName <> '', False));
end;
Заключение
В данной статье мы рассмотрели, как изменить логику сериализации в XML для использования имен атрибутов, предоставленных пользователем, вместо стандартных имен свойств. Это позволяет более гибко подходить к оптимизации размеров XML файлов, сохраняя при этом читаемость и структурированность данных.
При сериализации объектов в XML в Delphi, описана задача по изменению имен атрибутов для свойств, помеченных определенным пользовательским атрибутом, для использования в XML-структуре.
Комментарии и вопросы
Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS