семантика const для доступа к базе данных или файловой системе - PullRequest
7 голосов
/ 11 января 2012

Я регулярно использую const при работе со структурами данных в памяти и поддерживаю мой код постоянным, но я не уверен, как const должен применяться к более сложным объектам, таким как:

  • объекты, представляющие подключения к удаленным системам
  • объекты, поддерживаемые базой данных (которые могут загружать детали из базы данных по требованию)
  • объекты, поддерживаемые деревом каталогов на диске (с доступом к дереву каталогов, управляемому отдельной иерархией объектов)

Что должны означать const методы для подобных объектов? Я могу придумать пару возможностей:

  • "строгий" const - методы, которые не изменяют состояние в памяти, являются const. Однако это может привести к нарушению инкапсуляции, поскольку вызывающим сторонам потребуется знать, какие методы изменяют состояние соединения, а какие нет.
  • «логический» const - методы, которые не изменяют логическое состояние объекта, являются const. Тем не менее, это может потребовать пометить множество переменных состояния и кэширования как mutable. Хотя я понимаю, что это то, для чего mutable предназначен, но это похоже на хак. Кроме того, учитывая, что const означает «я обещаю не изменять это», представляется неправильным применять его, когда методы могут странным и чудесным образом изменять состояние соединения (при условии, что они поддерживают инкапсуляцию), результаты кэширования сколько угодно, выбрасывать исключения при сбое соединения и т. д.
  • Нет const - В свете предыдущих проблем, const просто не имеет большого значения для более сложных объектов?

Какой подход наиболее полезен? Что является наиболее распространенным?

1 Ответ

2 голосов
/ 12 января 2012

Это сложный вопрос. Я сейчас работаю над тем же. У меня есть большая структура данных в памяти, подкрепленная базой данных MySQL. Я начал с подхода «const везде, где это возможно», но на практике это происходит не очень часто:

  • Возможно, вы используете стороннюю библиотеку, которая не является правильной.
  • Не все SELECT операторы фактически доступны только для чтения. Например, SELECT GET_LOCK определенно изменяет состояние на стороне БД.
  • Я не встречал много программистов на C ++, которые могли бы правильно использовать mutable. У меня конечно нет особого опыта с этим. Будущие сопровождающие могут вызвать больше проблем, чем решит изменчивый. Вы знаете свою команду лучше всех, так что вам решать, хотите ли вы пойти по этому пути.

Я думаю, что const-объект с единственным изменяемым дескриптором базы данных может быть самым элегантным решением. Решите, что должен делать разумный объект const, и сделайте все эти функции const. Пользователям вашего класса нужно только знать, какие функции являются постоянными, а какие нет. Файл заголовка даст им это. Им не нужно знать почему конкретная функция является константной или неконстантной. Хотя я согласен, что куча изменчивых членов начинает выглядеть хакерской.

В моем случае мне пришлось отказаться от правильной константности. На константный объект были бы надеты наручники так, что он не смог бы сделать ничего полезного. Основываясь на своем многолетнем опыте, я подозреваю, что это обычно происходит на практике. Логическая константность - это хороший идеал (, и вам определенно стоит начать с нее, если вы строите с нуля ), но когда дело доходит до реального кода доставки, никакой константы не будет.

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