Форум по Delphi программированию

Delphi Sources



Вернуться   Форум по Delphi программированию > Все о Delphi > [ "Начинающим" ]
Ник
Пароль
Регистрация <<         Правила форума         >> FAQ Пользователи Календарь Поиск Сообщения за сегодня Все разделы прочитаны

Ответ
 
Опции темы Поиск в этой теме Опции просмотра
  #1  
Старый 03.11.2013, 17:59
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию Описание классов в Delphi

Здравствуйте уважаемые форумчане столкнулся с проблемой. Учусь в ВУзе. Дали вот такое задание:
Задача «Организация основной памяти»
* информационные объекты: страницы оперативной памяти (свойства – НомерСтраницы, Состояние)
* страницы объединяются в рамках объекта Сегмент (свойство – РазмерСегмента)
* сегменты объединяются в рамках объекта-контейнера ОсновнаяПамять (свойство – тип ОС).
Я описал классы, вот что получилось:
Код:
 класс TMemory
type
	TMemory = class(TObject)
private
// поля
	FNumber: integer; // приватное поле
	FPriznak: Boolean; // приватное поле
	public
// Конструктор
Constructor Create (const Number: integer; Priznak: boolean);
// методы чтения и записи свойств
	function GetNumber: integer; // получаем номер
	procedure SetNumber (const Value: integer); // задаём номер
	function GetPriznak: boolean; // получаем состояние
	procedure SetPriznak (const Value: boolean); // задаём состояние
end;
Код:
класс TElement
type
TElement = class(TObject)
private
// поля
	FMemory: TMemory; // приватное поле
	FNext: TElement; // приватное поле, указатель на следующий элемент
	public 
// конструкторы и деструкторы
	constructor Create (const Memory: TMemory);
	destructor Destroy; override;
// методы чтения и записи свойств
	function GetNext: TElement; // получаем следующий элемент стека
	procedure SetNext (const Value: TElement); // задаём следующий элемент стека
	function GetMemory: TMemory; // возвращаем значение поля FMemory
end;
Код:
класс TSegment
type
	TSegment = class(TObject)
private
// поля
	FFirst: byte; // приватное поле, вершинный элемент
	FNum: integer; // приватное поле, номер сегмента
	public
// конструкторы и деструкторы
	constructor Create (const Num: integer);
	destructor Destroy; override;
// методы чтения и записи свойств
	function GetFirst; TSegment; // получаем головной элемент
	function GetNum: integer; // получаем номер сегмента
	procedure SetNum (const Value: integer); // задаем номер сегмента
// методы
	procedure AddMemory (const Memory: TMemory); // добавляем элемент в стек
	function DelFirst: TElement; // удаляем вершинный элемент
	procedure Clear; // очищяем стек
end;
Код:
класс TSomeMemory
type
	TSomeMemory = class(TObject)
	Private
// поля
	FSome: array of  TMemory (динамический массив экземпляров класса TMemory)
	FCount: real (приватное поле, количество сегментов)
// конструкторы и деструкторы
	Constructor Create (initianCount)
	Destructor Destroy; override
// методы получения и установки значений свойств
	Function GetMemory (index: integer): TMemory (возвращаем объект класса TMemory)
	Function GetCount: integer (получаем количество сегментов)
// методы
	Function SegmentNO (No: integer):TSegment
	Function AddSL (No: integer): integer (добавляем в массив сегмент)
	Function DeleteSL (No: integeer): integer (удаляем из массива сегмент)
	Procedure SaveFile (const FileName: string) (сохраняем список в файле)
	Procedure LoadFile (const FileName: string) (загружаем список из файла)
	function WinInfo(Root_Key: HKEY; Key_Open, Key_Read: string): string
WinVers = 'Software\Microsoft\Windows\CurrentVersion' (читаем всё из реестра)
Преподаватель прокоментировал следующие ошибки: 1.Класс TMemory: название класса не соответствует его назначению
2.Класс TSegment: поле FFirst имеет неправильный тип
3.Класс TSomeMemory: массив имеет неправильный тип
первые 2 вродебы исправил, а с массивом проблемы. Подскажите пожалуйста. Спасибо.

Последний раз редактировалось Deman1986, 03.11.2013 в 18:51.
Ответить с цитированием
  #2  
Старый 03.11.2013, 19:05
lmikle lmikle вне форума
Модератор
 
Регистрация: 17.04.2008
Сообщения: 8,051
Версия Delphi: 7, XE3, 10.2
Репутация: 49089
По умолчанию

Я бы вообще не массив использовал, а TObjectList. А тип у него д.б. TSegment.
Ответить с цитированием
  #3  
Старый 03.11.2013, 19:09
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

Спасибо за ответ. Подскажите пожалуйста как описать правильно TObjectList. Просто я запутался уже, кучу литературы перечитал, а толку нет.

Последний раз редактировалось Deman1986, 03.11.2013 в 19:16.
Ответить с цитированием
  #4  
Старый 03.11.2013, 20:16
lmikle lmikle вне форума
Модератор
 
Регистрация: 17.04.2008
Сообщения: 8,051
Версия Delphi: 7, XE3, 10.2
Репутация: 49089
По умолчанию

Цитата:
Сообщение от Deman1986
Спасибо за ответ. Подскажите пожалуйста как описать правильно TObjectList. Просто я запутался уже, кучу литературы перечитал, а толку нет.

Ну, посмотри в справке в каком он юните описан, я не помню на вскидку, сам каждый раз смотрю

Использовать как и любой другой список (TList и т.д.) за исключением того, что если TObjectList является "владельцем" объектов в списке, то он сам вызывает деструктор при удалении объекта из списка. В остальном - все тоже самое, что и с любым списком.

У тебя и так работа со списком сегментов "спрятана" внутри классов, соотв. тебе надо будет переписать только саму работу с массива на список.

Да, и еще.
По мне, так у тебя как минимум один лишний класс. Я бы сделал так:
Код:
type
  TMemBlock = class
    // тут содержимое блока - занят или нет, базовый адрес и т.д.
  end;

  TSegemnt = class
  private
    FBlocks : TObjectList;
    // Ну и другие аттрибуты
  public
    property Blocks[Index : Integer] : TMemBlock read GetBlock; // Для прямого обращения к блоку по индексу
    ...
  end

  TRAM = class
  private
    FSegments : TObjectList;
  ...
  end;

Собственно, дальше, в зависимости от задачи, делаем методы инициализации.

Последний раз редактировалось lmikle, 03.11.2013 в 20:22.
Ответить с цитированием
  #5  
Старый 03.11.2013, 22:01
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

Спасибо большое за помощь, я с вами согласен, что лишний класс. Просто я еще обучаюсь Дельфи, раньше програмировал на Паскале.
Ответить с цитированием
  #6  
Старый 03.11.2013, 23:10
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

Вот получилось как то так))
Код:
класс TSomeMemory
type
	TSomeMemory = class(TObjectList)
	Private
// поля
	function GetItems (Index: integer): TSegment;
	procedure SetItems(Index: Integer; const Value: TSegment);
	public
	property Items[Index: Integer]: TSegment read GetItems write SetItems; default;
//чтение элементов списка будет происходить через метод GetItems,
//а запись - через SetItems
// методы
	function WinInfo(Root_Key: HKEY; Key_Open, Key_Read: string): string
WinVers = 'Software\Microsoft\Windows\CurrentVersion' // читаем всё из реестра
Ответить с цитированием
  #7  
Старый 04.11.2013, 06:59
lmikle lmikle вне форума
Модератор
 
Регистрация: 17.04.2008
Сообщения: 8,051
Версия Delphi: 7, XE3, 10.2
Репутация: 49089
По умолчанию

Цитата:
Сообщение от Deman1986
Вот получилось как то так))

Мне все-таки кажется, что наследоваться от TObjectList не стоит. Просто в таком случае хорошим тоном считается перекрытие всех методов родительского класса на работу со своими типами, что тебе явно не нужно (учиться кодировать "чисто" надо сразу, переучиваться потом гораздо сложнее). Просто напиши обертки только к тем методам, которые тебе нужны, а сам список спряч внутри класса (как я тебе и показал).

Кстати, если у тебя Дельфя одна из последних, то тогда можно сделать с помощью дженериков. В этом случае действительно компилятор за тебя сделает всю работу и можно использовать "наследование" (в кавычках, т.к. в случае использования дженериков это не совсем наследование, а инстанциация по типу).
Ответить с цитированием
  #8  
Старый 07.11.2013, 21:55
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

отправил преподавателю, он написал следующее:
1.Замечание 1 НЕ исправлено!
2.Замечание 2 исправлено НЕ правильно!
3.Замечание 3 исправлено НЕ правильно: куда исчез массив и все необходимые методы?
помогите исправить пожалуйста. Просто преподаватель настаивает на массиве. Спасибо за помощь

Последний раз редактировалось Deman1986, 07.11.2013 в 21:58.
Ответить с цитированием
  #9  
Старый 08.11.2013, 06:56
lmikle lmikle вне форума
Модератор
 
Регистрация: 17.04.2008
Сообщения: 8,051
Версия Delphi: 7, XE3, 10.2
Репутация: 49089
По умолчанию

Цитата:
Сообщение от Deman1986
отправил преподавателю, он написал следующее:
1.Замечание 1 НЕ исправлено!
2.Замечание 2 исправлено НЕ правильно!
3.Замечание 3 исправлено НЕ правильно: куда исчез массив и все необходимые методы?
помогите исправить пожалуйста. Просто преподаватель настаивает на массиве. Спасибо за помощь

Ну и сделай, как он хочет. Заодно можешь передать ему от меня, что он дурак и программировать не умеет, ну или не умеет грамотно ставить задачу.
1. Переименуй класс в TPage или TMemoryPage
2. Тип д.б. как раз TPage(TMemoryPage).
3.
а) Убираешь TElement, он не нужен.
б) В TSegment делаешь массив для страниц памяти, кол-во, видимо, надо задавать в конструкторе, собственно, это размер сегмента.
в) В TSomeMemory тоже делаешь массив для сегментов.
Вроде так.
Ответить с цитированием
  #10  
Старый 08.11.2013, 08:18
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

А набросать можете у меня с массивами туговато))
Ответить с цитированием
  #11  
Старый 11.11.2013, 20:32
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

Я подумал и вот что получилось:
Код:
класс TSegment
type
	TSegment = class(TObject)
private
// поля
	FFirst: TPage; // приватное поле, вершинный элемент
	ACount: integer; // приватное поле, кол-во элементов
	public
// конструкторы и деструкторы
	constructor Create (ACount: integer); // инициализация
              destructor Destroy; override; // уничтожение
// методы
              procedure SetCount (ACount: integer); // установка кол-во элем.
              procedure Reset // обнуление данных
end;
Поправьте если не правильно

Последний раз редактировалось Deman1986, 11.11.2013 в 20:37.
Ответить с цитированием
  #12  
Старый 12.11.2013, 06:52
lmikle lmikle вне форума
Модератор
 
Регистрация: 17.04.2008
Сообщения: 8,051
Версия Delphi: 7, XE3, 10.2
Репутация: 49089
По умолчанию

Как я понимаю, связанный список тут не нужен.
Тогда сегмент будет примерно так:


Код:
type
  TSegment = class(TObject)
  private
    FPages : Array Of TPage;
    function GetCount : Integer;
    function GetPage(Index : Integer) : TPage;
  public
    // конструкторы и деструкторы
    constructor Create (ACount: integer); virtual;// инициализация
    destructor Destroy; override; // уничтожение

    property Count : Integer read GetCount;
    property Pages[Index : Integer] : TPage read GetPage;

    procedure ClearAll;
  end;

...

constructor TSegment.Create(ACount : Integer);
var
  I : Integer;
begin
  inherited Create;
  SetLength(FPages,ACount);
  For I := Low(FPages) To High(FPages) Do
    FPages[i] := TPages.Create;
end;

destructor TSegment.Destroy;
var
  I : Integer;
begin
  For I := Low(FPages) To High(FPages) Do
    FPages[i].Free;
  SetLength(FPages,0);
  inherited;
end;

function TSegment.GetCount : Integer;
begin
  Result := Length(FPages);
end;

function TSegment.GetPage(Index : Integer) : TPage;
begin
  Result := FPages[Index];
end;

procedure TSegment.ClearAll;
var
  I : Integer;
begin
  For I := Low(FPages) To High(FPages) Do
    FPages[i].Clear;
end;

Это вариант с пресозданием страниц.
Можно сделать вариант с выделением памяти при первом обращении.
Еще можно сделать в таком случае сборщик памяти, когда занятые куски собираются в начало сегмента.

Вообще, там много можно чего сделать. Фактически, можно написать свой небольшой менеджер памяти.
Ответить с цитированием
Этот пользователь сказал Спасибо lmikle за это полезное сообщение:
Deman1986 (12.11.2013)
  #13  
Старый 12.11.2013, 21:03
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

Спасибо Вам большое. Вы настоящий человек. Буду думать над последним классом TSomeMemory.
Ответить с цитированием
  #14  
Старый 19.11.2013, 21:18
Deman1986 Deman1986 вне форума
Прохожий
 
Регистрация: 03.11.2013
Сообщения: 32
Версия Delphi: Delphi 7
Репутация: 10
По умолчанию

Вот описал я класс TRam (массив для сегментов):
Код:
класс TRam
type
	TRam = class(TObject)
private
// поля
	FRam: Array of  TSegment; // динамический массив 
	FCount: real; // приватное поле, количество сегментов
// конструкторы и деструкторы
	constructor Create (ACount: integer);  // инициализация
	destructor Destroy; override;
// методы
	procedure SetCount (ACount: integer): // установка количества элементов
	procedure Reset; // обнуление данных
        function WinInfo(Root_Key: HKEY; Key_Open, Key_Read: string): string;
WinVers = 'Software\Microsoft\Windows\CurrentVersion' // читаем всё из реестра
end;
Ответить с цитированием
  #15  
Старый 19.11.2013, 21:41
Аватар для poli-smen
poli-smen poli-smen вне форума
Профессионал
 
Регистрация: 06.08.2012
Адрес: Кривой Рог
Сообщения: 1,791
Версия Delphi: Delphi 7, XE2
Репутация: 4415
По умолчанию

Цитата:
Сообщение от Deman1986
Вот описал я класс TRam (массив для сегментов):
Код:
класс TRam
type
	TRam = class(TObject)
private
// поля
	FRam: Array of  TSegment; // динамический массив 
	FCount: real; // приватное поле, количество сегментов
// конструкторы и деструкторы
	constructor Create (ACount: integer);  // инициализация
	destructor Destroy; override;
// методы
	procedure SetCount (ACount: integer): // установка количества элементов
	procedure Reset; // обнуление данных
        function WinInfo(Root_Key: HKEY; Key_Open, Key_Read: string): string;
WinVers = 'Software\Microsoft\Windows\CurrentVersion' // читаем всё из реестра
end;
Почему FCount типа real? Разве количество сегментов может быть дробным числом?
Почему конструктор и деструктор в приватной секции?
Идентификатор WinVers как вообще попал сюда в объявление класса?
В объявлении метода SetCount в конце двоеточие вместо точки с запятой.
Ответить с цитированием
Ответ


Delphi Sources

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск
Опции просмотра

Ваши права в разделе
Вы не можете создавать темы
Вы не можете отвечать на сообщения
Вы не можете прикреплять файлы
Вы не можете редактировать сообщения

BB-коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.
Быстрый переход


Часовой пояс GMT +3, время: 01:01.


 

Сайт

Форум

FAQ

RSS лента

Прочее

 

Copyright © Форум "Delphi Sources" by BrokenByte Software, 2004-2023

ВКонтакте   Facebook   Twitter