Форум: "Основная";
Текущий архив: 2010.02.14;
Скачать: [xml.tar.bz2];
ВнизДополнение перечисления Найти похожие ветки
← →
Kolan © (2009-03-16 11:32) [0]Здравствуйте!
У меня есть набор команд, которые закодированы числами. Часть команд является базовой, а часть может изменяться. Я бы хотел описать в одном модуле перечисление с базовым набором команд, а в других модулях иметь возможность расширять его.
Примерно так:
base.pas
TCommandTypes =
(
mtDeviceError = $FF,
mtVersionInfoRequest = $00,
mtVersionInfoAnswer = $80,
);
special.pas
TCommandTypes =
(
mtOperationModeRequest = $01,
mtOperationModeAnswer = $81,
mtImpedanceMeasurmentStartRequest = $02,
mtMeasurmentStartAnswer = $82,
...
);
Такое дополнение перечислений хочется сделать для того, что бы в базовом модуле создать набор функций, которые бы принималиTCommandTypes
и работали бы как для команд из базового модуля, так и для команд из любого другого и вместе с тем работала бы проверка времени компиляции.
Понятно, что если я поступлю так как в примере, то базовый набор команд будет просто закрыт и ничего не получится.
Как можно добиться желаемого?
← →
Медвежонок Пятачок © (2009-03-16 11:36) [1]одно полное длинное перечисление.
там, где хочется контроль по ограниченному перечню - ассерт
← →
Palladin © (2009-03-16 11:52) [2]
> Kolan © (16.03.09 11:32)
Чем простые константы не устроили?
← →
MsGuns © (2009-03-16 11:58) [3]Интересно, откуда возникло такое желание, ведь суть перечислений - это именно постоянность
← →
Kolan © (2009-03-16 12:40) [4]>Чем простые константы не устроили?
Из всех вариантов этот мне нравится больше всего, но плохо, что в методах придется писатьFoo(Command: Integer)
, а неFoo(Command: TCommandTypes)
.
MsGuns, желание возникло так как сабжевые команды — это команды их протокола разных устройств. Часть таких команд базовая и есть во всех устройствах, а другая часть у каждого устройства своя.
>одно полное длинное перечисление.
Это невозможно сделать, я не знаю какие команды будут у устройств, которые появятся, скажем, в следующем году.
← →
Palladin © (2009-03-16 12:50) [5]
> Kolan © (16.03.09 12:40) [4]
И в чем проблемы?Type
TCommandType=type Integer;
Const
mtDeviceError:TCommandType = $FF
← →
Медвежонок Пятачок © (2009-03-16 12:54) [6]Это невозможно сделать, я не знаю какие команды будут у устройств, которые появятся, скажем, в следующем году.
Тогда стоит подумать вообще о логичности выбора перечисления как нудного типа.
Хотя не вижу препятствий.
У меня тодже команды и тоже перечисления, причем даже без уточнения значений. Перечень команд постоянно из месяца в месяц растет.
И ничему этот рост не мешает.
← →
Kolan © (2009-03-16 12:59) [7]Palladin, отлично! Проверки типа нет, но подсказка при вызове функции выводится вполне понятная. Я думаю путаницы не возникнет, поэтому считаю, что ответ получил — благодарю.
← →
Ega23 © (2009-03-16 13:08) [8]
> Проверки типа нет,
ЕМНИП, когда type Integer - проверка есть. Хотя тут уже могу ошибаться.
← →
Kolan © (2009-03-16 13:38) [9]Ega, я проверил:
TForm2 = class(TForm)
...
public
{ Public declarations }
procedure foo(command: TCommandType);
end;
procedure TForm2.foo(command: TCommandType);
begin
ShowMessage(IntToStr(command));
end;
procedure TForm2.FormCreate(Sender: TObject);
begin
foo(1);
end;
Единичку показал. Так что проверки нет. Но я думаю, что правильный префикс и подсказка при вызове метода поможет избежать проблем.
← →
Dimka Maslov © (2009-03-16 13:43) [10]Проверка производится только когда переменная передаётся в функцию через var. В этом случае integer и type integer трактуются как разные типы.
← →
Kolan © (2009-03-16 13:50) [11]Возникла проблема в операторе case.
Если объявлять константы так:
type
TCommandType = type Integer;
const
ctDeviceError: TCommandType = $FF;
...
И использовать так:function TCustomFreGrafDeviceProtocol.DefineCommandType(
Command: TCommandType): string;
begin
case Command of
ctDeviceError:
Result := rsDeviceError;
...
То компилятор говорит, что:Constant expression expected
в строке сctDeviceError:
. Если убрать из объявления константTCommandType
, то есть написать простоctDeviceError = $FF;
, то скомпилировать удается. Но в этом случае получается, что константы не связаны с типом TCommandType.
Как объяснить компилятору, что это константа?
← →
Медвежонок Пятачок © (2009-03-16 14:08) [12]зачем все это?
иметь перечисление TEnum = (one,two,three)
и массив array[TEnum] (и то если важно десятичное значение).
и все.
Для алгоритма значение не нужно, ну а девайс посылать прямо значения енума - не очень логично.
← →
Kolan © (2009-03-16 14:37) [13]Медвежонок Пятачок, я не понимаю что вы предлагаете.
Попробую объяснить еще раз.
Мне хочется написать методFoo(Command: TCommandType);
. Command — это некоторое число которому надо дать осмысленное имя.
Проблема в том, что с одной стороны в одном модуле число$90
может означать одно, а в другом другое и программист должен видеть и понимать что от него хотят и что он передал, а с другойFoo
должно работать с любым переданным числом.
Причем тут массив — не ясно.
>...ну а девайс посылать прямо значения енума - не очень логично.
Почему не логично? Я думаю, что записьSendCommand(1);
гораздо хуже чем записьSendCommand(ctBlowUp);
. Вы так не считаете?
← →
Медвежонок Пятачок © (2009-03-16 14:57) [14]Причем тут массив — не ясно.
TEnum = (one,two,three)
все ясно и понятно. элементы перечисления с осмысленными именами.
и кейс доволен.
← →
Kolan © (2009-03-16 15:40) [15]Медвежонок Пятачок, как теперь в другом модуле добавить в TEnum еще four и five?
← →
Медвежонок Пятачок © (2009-03-16 16:32) [16]если в другом модуле, то это будет уже другой тип
← →
Kolan © (2009-03-16 16:37) [17]Тогда мне придется писать несколько функций для обработки этих констант, а это плохое решение.
← →
Медвежонок Пятачок © (2009-03-16 16:39) [18]я честно говоря не понимаю, почему расширение базового перечисления может чем-то помешать базовому модулю.
← →
Германн © (2009-03-16 17:00) [19]
> Как объяснить компилятору, что это константа?
>
Это "типизированная" константа. А её значение можно изменить в рантайме. И как тут быть компилятору?
← →
Kolan © (2009-03-17 10:33) [20]Герман, если спросить меня, то я бы не делал констант, которые могут изменяться :).
Пока просто убрал тип, и сделал документацию, но лучше бы код сам себя документировал.
Медвежонок Пятачок, потому что метод в базовом модуле, который принимает тип TCommandType из этого же базового модуля не сможет принять тип TCommandType из другого модуля, так как это разные типы.
← →
Медвежонок Пятачок © (2009-03-17 17:58) [21]Вот поэтому я и не предлагал и не предлагаю "расширять" перечисление в других модулях.
Одно перечисление на все про все.
Растущее и удлинняющееся от версии к версии программы.
← →
Германн © (2009-03-18 00:07) [22]
> Kolan © (17.03.09 10:33) [20]
>
> Герман, если спросить меня, то я бы не делал констант, которые
> могут изменяться :).
Это было введено в Паскаль очень давно. И поменьше, но тоже давно, объявлено Борландом как оставленное для обратной совместимости, и что в новых проектах использование типизированных констант не рекомендуется!
Так что сам виноват, очкарик, что вляпался. :)
← →
SPeller © (2009-03-18 07:34) [23]
> как теперь в другом модуле добавить в TEnum еще four и five?
Очень просто. Руками. Берешь и добавляешь. В старом модуле ничего не поломается если там нет массивов на основе твоего старого перечисления (array[TEnum]) и все твои if и case предусматривают возможность появления значения вне рамок перечисления, определенных на этапе компиляции.
← →
SPeller © (2009-03-18 07:36) [24]Это если понятие "модуль" равно понятию "длл".
← →
SPeller © (2009-03-18 07:37) [25]А если всё внутри одного проекта, то, имхо, только константы с префиксами. Если неохота юзать переменные константы.
← →
Kolan © (2009-03-19 10:12) [26]
> Это если понятие "модуль" равно понятию "длл".
Понятие модуль равно понятию модуля (unit).
> Растущее и удлинняющееся от версии к версии программы.
Так нет версий программы. Это библиотечный модуль, который используют много кто.
> А если всё внутри одного проекта, то, имхо, только константы
> с префиксами.
Так и поступил.
> Так что сам виноват, очкарик, что вляпался. :)
Давненько я тут не был. :)
Вопрос считаю закрытым, благодарю за обсуждение.
← →
Медвежонок Пятачок © (2009-03-19 10:51) [27]Так нет версий программы. Это библиотечный модуль, который используют много кто.
Пусть используют.
С одним длинным перечислением.
если у разработчиков нет массивов по перечислению, они и не заметят изменений типа перечисления.
Страницы: 1 вся ветка
Форум: "Основная";
Текущий архив: 2010.02.14;
Скачать: [xml.tar.bz2];
Память: 0.52 MB
Время: 0.005 c