Переопределение методов Equals и ToString на примере классов Person и Student
Материал из Вики ИТ мехмата ЮФУ
Назначение
Использован в конспекте лекций по основам программирования в теме «полиморфизм».
Описание
Представлена реализация следующих классов:
Тексты модулей
PersonUnit
unit PersonUnit;
interface
uses System;
const
/// Минимальный возможный возраст
MIN_AGE = 1;
/// Максимальный возможный возраст
MAX_AGE = 120;
// --------------------------------------------- Person -------------------------------------------
type
/// Персона
Person = class
private
/// Имя
fName: string;
/// Возраст
fAge: integer;
/// Устанавливает имя равным name, если оно не пусто
procedure SetName(name: string);
/// Устанавливает возраст равным age, если он положителен
/// и не превышает максимально возможного (MAX_AGE)
procedure SetAge(age: integer);
public
/// <summary>
/// Создает новую персону
/// </summary>
/// <param name="Name">Имя (пустое недопустимо)</param>
/// <param name="Age">Возраст (отрицательный недопустим)</param>
constructor Create(Name: string; Age: integer);
/// Возвращает истину, если текущий объект равен по значению объекту o
function Equals(o: object): boolean; override;
/// Возвращает строковое представление персоны
function ToString: string; override;
/// Имя
property Name: string read fName write SetName;
/// Возраст
property Age: integer read fAge write SetAge;
/// Выводит на консоль информацию о персоне
procedure Print; virtual;
end;
implementation
// --------------------------------------------- Person -------------------------------------------
procedure Person.SetName(name: string);
begin
if name <> '' then
fName := name
else
raise new Exception(
'Попытка задать персоне пустое имя.');
end;
procedure Person.SetAge(age: integer);
begin
if age > 0 then
fAge := age
else
raise new Exception(
'Выход за границы диапазона допустимого возраста [' +
MIN_AGE.ToString + '..' + MAX_AGE.ToString + '].');
end;
constructor Person.Create(Name: string; Age: integer);
begin
SetName(Name);
SetAge(Age);
end;
{Возвращает истину, если текущий объект равен по значению объекту o}
function Person.Equals(o: object): boolean;
begin
if o = nil then
Result := false
else if GetType <> o.GetType then
Result := false
else
begin
var p := Person(o);
Result := (Name = p.Name) and (Age = p.Age);
end;
end;
function Person.ToString: string;
begin
Result := Format(
'Имя: {0} Возраст: {1} ',
fName, fAge);
end;
procedure Person.Print;
begin
WriteFormat(
'Имя: {0} Возраст: {1} ',
fName, fAge);
end;
end.
StudentUnit
unit StudentUnit;
interface
uses System, PersonUnit;
const
/// Первый курс
FIRST_COURSE = 1;
/// Последний курс для студентов младших курсов
LAST_UNDERGRADUATE_COURSE = 4;
// -------------------------------------------- Student -------------------------------------------
type
/// Студент
Student = class (Person)
private
///Курс
fCourse: integer;
///Группа
fGroup: integer;
/// Устанавливает номер группы равным group,
/// если он неотрицателен
procedure SetGroup(group: integer);
public
/// <summary>
/// Создает нового студента
/// </summary>
/// <param name="Name">Имя (пустое недопустимо)</param>
/// <param name="Age">Возраст (отрицательный недопустим)</param>
/// <param name="Course">Курс (отрицательный или больший LAST_UNDERGRADUATE_COURSE недопустим)</param>
/// <param name="Group">Группа (отрицательная недопустима)</param>
constructor Create(Name: string; Age, Course, Group: integer);
/// Переводит студента на следующий курс, если он меньше LAST_UNDERGRADUATE_COURSE
procedure NextCourse;
/// Возвращает истину, если текущий объект равен по значению объекту o
function Equals(o: object): boolean; override;
/// Возвращает строковое представление студента
function ToString: string; override;
/// Курс — доступ только на чтение
property Course: integer read fCourse;
/// Группа
property Group: integer read fGroup write SetGroup;
/// Выводит на консоль информацию о студенте
procedure Print; override;
end;
implementation
// -------------------------------------------- Student -------------------------------------------
{Устанавливает номер группы равным Group, если он неотрицателен}
procedure Student.SetGroup(group: integer);
begin
if group > 0 then
fGroup := group
else
raise new Exception(
'Попытка присвоить номеру группы отрицательное значение.');
end;
constructor Student.Create(Name: string; Age, Course, Group: integer);
begin
inherited Create(name, age);
SetGroup(Group);
if (Course >= FIRST_COURSE) and (Course <= LAST_UNDERGRADUATE_COURSE) then
fCourse := Course
else
raise new Exception(
'Выход за границы диапазона допустимых курсов [' +
FIRST_COURSE.ToString + '..' + LAST_UNDERGRADUATE_COURSE.ToString + ']!');
end;
{Переводит студента на следующий курс, если он меньше LAST_UNDERGRADUATE_COURSE}
procedure Student.NextCourse;
begin
if fCourse < LAST_UNDERGRADUATE_COURSE then
fCourse += 1
else
raise new Exception(
'Выход за границы диапазона допустимых курсов [' +
FIRST_COURSE.ToString + '..' + LAST_UNDERGRADUATE_COURSE.ToString + ']!');
end;
{Возвращает истину, если текущий объект равен по значению объекту o}
function Student.Equals(o: object): boolean;
begin
Result := inherited Equals(o);
if Result then
begin
var s := Student(o);
Result := (Course = s.Course) and (Group = s.Group);
end;
end;
function Student.ToString: string;
begin
Result := inherited ToString + Format(
'Курс: {0} Группа: {1} ',
fCourse, fGroup);
end;
procedure Student.Print;
begin
inherited Print;
WriteFormat(
'Курс: {0} Группа: {1} ',
fCourse, fGroup);
end;
end.