Должна ли выбранная ООП-абстракция быть как можно ближе к жизни? - PullRequest
0 голосов
/ 16 июля 2010

Я разрабатываю библиотеку для своего приложения, которая обертывает подсистему смарт-карт Windows.

Физически существует смарт-карта, которая подключена к устройству чтения смарт-карт, а устройство чтения - к ПК.Существует много типов смарт-карт (например, карты Javacards и .NET).Одна из идей для разработки этого заключается в следующем:

TReaderListBase <- TReaderListJavaCard </p>

TReaderBase <- TReaderJavaCard </p>

TSmartcardBase <- TJavaCard </p>

Список читателей Get() метод возвращает считыватель по индексу или по имени, а метод Connect () считывателя возвращает экземпляр объекта карты для работы с ним.

Проблема в том, что хотя существуют физически действительно разные типы смарт-карт, существуетна самом деле только один тип читателя, который может прочитать их все.TReaderListJavaCard предназначался только для выполнения функций поиска с использованием определенных атрибутов Javacard.И TReaderJavaCard существует только для того, чтобы возвращать экземпляр класса TJavaCard вместо TSmartcardBase, возвращаемого TReaderBase в методе Connect ().

Также в этом дизайне есть некоторые логические дыры, например, когда вы подключаете смарт-карту из устройства чтения, может показаться логичным, что экземпляр потомка TSmartcardBase немедленно уничтожается, потому что имя класса говорит, что он олицетворяет собой саму карту, и этой карты больше нет.

Tt работает точно.Но кажется ли эта схема логичной?

У меня было предложение от моего друга изменить структуру системы следующим образом:

Пропустить считыватели, создать класс TSmartcardProxyObjectBase, спуститься с него TJavaCardProxyObject и добавить все методы впоиск и подключение к ним карточек.Что-то вроде пакета «все в одном».Эта абстракция выглядит хорошо, потому что CardProxyObject действительно может что-то искать, подключаться к чему-либо, находиться в автономном режиме (если удалена карта, к которой он подключен) и т. Д. Но этот дизайн нарушает SRP, потому что один класс выполняет поиск связи и поиск объектов.Если я захочу отсоединить функции поиска от него и получу ту же схему, что и в первом случае (он просто добавит что-то, что может работать с читателями).

Мой друг говорит, что мы на самом деле не работаемнепосредственно с читателями, и основная цель библиотеки - работать с карточками, поэтому мы должны скрывать читателей от пользователя библиотеки.

Поскольку такие проекты - это то, из чего можно научиться проектировать ООП, я заинтересован в нахождении чрезвычайно красивого решения.;)

Надеюсь, я объяснил все понятно;)

Есть третий способ сделать это.Пусть это будут финальные классы ReaderList и Reader.Но в читателе не должно быть метода Connect ().Вместо этого я могу реализовать метод Use () или PutOnline () в классе смарт-карт, чтобы использовать этот конкретный ридер для связи, эффективно скрывая низкоуровневый вызов SCardConnect от пользователя.Функции поиска могут быть перемещены в некоторый вспомогательный класс (например, TJavaCardLocatorService).Или я должен сделать их статическими членами класса TJavaCardProxyObject?Что-то вроде TJavaCardProxyObject.AttachToCardWithAID (ReaderList), но имя выглядит также нелогичным и, опять же, кажется, нарушает SRP.

Что вы думаете?В любом случае, важно ли иметь хорошую архитектуру в реальных проектах, или я просто теряю время, пытаясь научиться чему-то неважному?

Ответы [ 2 ]

2 голосов
/ 16 июля 2010

В каком-то смысле важно иметь хорошую архитектуру в реальных проектах, или я просто трачу время на изучение чего-то неважного?

Если вы создаете проект, ваши пользовательские интерфейсы очень важны.

Если вы создаете библиотеку ООП, ваш API очень важен.

В обоих случаях вопрос, на который вы пытаетесь ответить, таков: «Легко ли это (API, экран, отчет) использовать?

Определенно стоит потратить время на то, чтобы сделать API максимально полезным.

Что касается вашего заглавного вопроса, нет, необязательно, чтобы абстракция ООП была как можно ближе к жизни. Однако чем ближе API к тому, как люди используют реальные объекты, тем лучше.

1 голос
/ 16 июля 2010

Заявление вашего друга в основном на правильном пути.

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

Неважно, прав ли ваш друг или нет;это именно то, о чем вы должны думать, когда пишете абстракцию.Как пользователь библиотеки будет думать о задаче, которую он использует для выполнения библиотеки?Выясните это, затем реализуйте абстракцию как можно ближе к этому.

Что касается нарушений SRP при создании «пакета все-в-одном», в настоящее время в модели для программирования «Программист» отвечает не только за написание кода, но и за компиляцию, загрузку, запуск исопоставление вывода кода.Это было не так давно, когда этими второстепенными задачами занимался совершенно другой человек (или, возможно, несколько человек).Я уверен, что в SO есть люди, которые помнят, как брали перфокарты в компьютерный отдел.Какая модель нарушает ПСП?Ответ: ни один.Концепция того, за что отвечает программист, изменилась за последние 30 лет.

Если вы найдете модель, которая лучше подходит и которая меняет концепцию единой ответственности, это нормально, потому что режим, вероятно, является лучшей абстракцией для пользователей вашей библиотеки.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...