А существует универсальная функция сравнения объектов?

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Re: А существует универсальная функция сравнения объектов?

Сообщение leo_bsv » 09.01.2012 21:11:13

ну вот примерно что получается:
Код: Выделить всё
type
  { TOdtTableLineProperties }
  TOdtTableLineProperties = class
    private
      FBreakAfter: TBreak;  // атр, разрыв страницы после колонки/строки
      FBreakBefore: TBreak; // атр, разрыв страницы до колонки/строки
      FUseOptimalSize: boolean; // атр, оптимальная ширина/высота колонки/строки
    public
      constructor Create;
      destructor Destroy;
      function Equal(aObject: TOdtTableLineProperties): boolean; // УРИВЕРСАЛЬНАЯ ФУНКЦИЯ СРАВНЕНИЯ
      property BreakAfter: TBreak read FBreakAfter write FBreakAfter;
      property BreakBefore: TBreak read FBreakBefore write FBreakBefore;
      property UseOptimalSize: boolean read FUseOptimalSize write FUseOptimalSize;
  end;

type
  { TOdtTableColumnProperties }
  TOdtTableColumnProperties = class(TOdtTableLineProperties)
    private
      FSymbol: string;      // часть значения атрибута - символьное обозначение колонки A,B,C...
      FWidth: TSizes;       // атр, абс определяет фикс ширину колонки
      FRelWidth: TSizes;    // атр, относительная ширина колонки
    public
      constructor Create;
      destructor Destroy;
      property Symbol: string read FSymbol write FSymbol;
      property Width: TSizes read FWidth write FWidth;
      property RelWidth: TSizes read FRelWidth write FRelWidth;
  end;

type
  TOdtTableColsProperties = Specialize TFPGList<TOdtTableColumnProperties>; // массив свойств колонок

type
  { TOdtTableRowProperties }
  TOdtTableRowProperties = class(TOdtTableLineProperties)
    private
      FBackgroundColor: TColor;  // цвет строки
      FKeepTogether: TKeepWithNext; // атр, не отрывать строку от соседних?
      FMinHeight: TSizes;        // атр, минимальная высота строки
      FHeight: TSizes;           // атр, высота строки
      //FBackgroundImage  // не реализовано
    public
      constructor Create;
      destructor Destroy;
      property BackgroundColor: TColor read FBackgroundColor write FBackgroundColor default 0;
      property KeepTogether: TKeepWithNext read FKeepTogether write FKeepTogether;
      property MinHeight: TSizes read FMinHeight write FMinHeight;
      property Height: TSizes read FHeight write FHeight;
  end;

...
...
...
// УНИВЕРСАЛЬНАЯ ФУНКЦИЯ СРАВНЕНИЯ
function TOdtTableLineProperties.Equal(Obj: TOdtTableLineProperties): boolean;
begin
  If Obj is TOdtTableColumnProperties then
    ...
  If Obj is TOdtTableRowProperties then
    ...
end;



Добавлено спустя 31 минуту 59 секунд:
функция должна выглядеть примерно так
Код: Выделить всё
  if FBreakAfter<>Obj.BreakAfter then exit(false);
  if FBreakBefore<>Obj.BreakBefore then exit(false);
  if FUseOptimalSize<>Obj.UseOptimalSize then exit(false);
  if Obj is TOdtTableColumnProperties then begin
    if FSymbol<>TOdtTableColumnProperties(Obj).Symbol then exit(false);
    if Changed(FWidth,TOdtTableColumnProperties(Obj).Width) then exit(false);
    if Changed(FRelWidth,TOdtTableColumnProperties(Obj).RelWidth) then exit(false);
  end;
  if Obj is TOdtTableRowProperties then begin
    if FBackgroundColor<>TOdtTableRowProperties(Obj).BackgroundColor then exit(false);
    if FKeepTogether<>TOdtTableRowProperties(Obj).KeepTogether then exit(false);
    if Changed(FMinHeight,TOdtTableRowProperties(Obj).MinHeight) then exit(false);
    if Changed(FHeight,TOdtTableRowProperties(Obj).Height) then exit(false);
  end;
  result:=true; 

однако доступа к свойствам классов-потомков видимо нет... как-то можно вытянуть их свойства?

Добавлено спустя 4 минуты 24 секунды:
видимо придётся переопределять эту функцию для потомков и переносить конфликтные строки...
Аватара пользователя
leo_bsv
постоялец
 
Сообщения: 276
Зарегистрирован: 04.08.2010 16:26:10
Откуда: Йошкар-Ола

Re: А существует универсальная функция сравнения объектов?

Сообщение alexs » 10.01.2012 22:32:52

используй вместо дерективы private - protected. Она именно для этого предназначена.

И ещё - но то конечно дело вкуса:

exit(false); - не красиво.
Поставь первой строкой процедуры
result:=false;
А exit пусть будет без параметра.
Читабельность кода будет лучше.
Аватара пользователя
alexs
долгожитель
 
Сообщения: 4064
Зарегистрирован: 15.05.2005 23:17:07
Откуда: г.Ставрополь

Re: А существует универсальная функция сравнения объектов?

Сообщение leo_bsv » 11.01.2012 01:12:57

protected - доступ только потомкам...
т.е. в родительском классе объявляю в protected функцию
Код: Выделить всё
type
  { TOdtTableLineProperties }
  TOdtTableLineProperties = class
  protected
    ...
    function Equal(Obj: TOdtTableLineProperties): boolean;

дальше пишу саму функцию...
Код: Выделить всё
function TOdtTableLineProperties.Equal(Obj: TOdtTableLineProperties): boolean;
begin
  result:=false;
  if FBreakAfter<>Obj.BreakAfter then exit;
  if FBreakBefore<>Obj.BreakBefore then exit;
  if FUseOptimalSize<>Obj.UseOptimalSize then exit;
  if Obj is TOdtTableColumnProperties then begin
    if FSymbol<>TOdtTableColumnProperties(Obj).Symbol then exit;                     // при этом FSymbol свойство класса TOdtTableColumnProperties
    if Changed(FWidth,TOdtTableColumnProperties(Obj).Width) then exit;            // при этом FWidth свойство класса TOdtTableColumnProperties
    if Changed(FRelWidth,TOdtTableColumnProperties(Obj).RelWidth) then exit;  // при этом FRelWidth свойство класса TOdtTableColumnProperties
  end;
  if Obj is TOdtTableRowProperties then begin
    if FBackgroundColor<>TOdtTableRowProperties(Obj).BackgroundColor then exit; // при этом FBackgroundColor свойство класса TOdtTableRowProperties
    if FKeepTogether<>TOdtTableRowProperties(Obj).KeepTogether then exit;          // при этом FKeepTogether свойство класса TOdtTableRowProperties
    if Changed(FMinHeight,TOdtTableRowProperties(Obj).MinHeight) then exit;        // при этом FMinHeight свойство класса TOdtTableRowProperties
    if Changed(FHeight,TOdtTableRowProperties(Obj).Height) then exit;                  // при этом FHeight свойство класса TOdtTableRowProperties
  end;
  result:=true;
end;   

код не рабочий, компилятор пишет
odfproc.pas(745,41) Error: Identifier not found "FSymbol"

процедура то определена в классе TOdtTableLineProperties, в которой не все проверяемые свойства... как быть :?:
p.s.: потомки то понятное дело к родителю обратяться, а тут получается наоборот - из родителя к свойствам потомков запрос... это вообще реально :?:

Добавлено спустя 5 минут 3 секунды:
хотя конечно я так то уже написал в каждом дочернем классе переопределяющую процедуру:
Код: Выделить всё
function TOdtTableColumnProperties.Equal(Obj: TOdtTableColumnProperties
  ): boolean;
begin
  result:=false;
  if FSymbol<>TOdtTableColumnProperties(Obj).Symbol then exit;
  if Changed(FWidth,TOdtTableColumnProperties(Obj).Width) then exit;
  if Changed(FRelWidth,TOdtTableColumnProperties(Obj).RelWidth) then exit;
  result := inherited Equal(Obj);
end;

просто интересно, можно ли в одной всё сразу описать... :)
Аватара пользователя
leo_bsv
постоялец
 
Сообщения: 276
Зарегистрирован: 04.08.2010 16:26:10
Откуда: Йошкар-Ола

Пред.

Вернуться в Lazarus

Кто сейчас на конференции

Сейчас этот форум просматривают: Alex2013 и гости: 239

Рейтинг@Mail.ru