![]() |
|
Модераторы: Daevaorn |
![]()
|
|
| EvilsInterrupt |
|
||||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
При разработке класса по работе с каким-либо форматом файла мы часто пользуемся стримами чтобы читать\писать из\в файл. До сих пор использую способ передачи базового класса стрима по ссылке в конструктор класса. Мне перестает нравиться по разным причинам и хочу узнать опыт других разработчиков, послушать их идиомы и методы.
Чтобы не было слишком излишне абстрактно возьмем задачу по разработке класса по работе с форматом "Super Format", ниже в коде приведены декларации заголовков. Также давайте напишем, который должен хранить и возвращать эти заголовки пользовательскому коду.
Задача: Как-либо передать данные из\ в стрим во внутренние приватные члены firstHeader и secondHeaders. Другими словами как организовать работу со стримом, чтобы писать и записывать данные в эти приватные заголовки? Пока вижу такие варианты:
Возможно Вы предложите еще, не стесняйтесь ) |
||||
|
|||||
| mes |
|
|||
|
любитель ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 7954 Регистрация: 14.1.2006 Репутация: 144 Всего: 250 |
stream<<any_format(image) |
|||
|
||||
| EvilsInterrupt |
|
|||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
Я отказался от такого варианта, т.к. менее читабелен чем read()/write() . |
|||
|
||||
| volatile |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 2107 Регистрация: 7.1.2011 Репутация: 37 Всего: 85 |
1,
как это менее читабелен? Это же устоявшаяся практика в С++... 2. Как это вы пишете по константной ссылке? И развивая мысль, если же возвращать не контантную ссылку, то смысла делать члены приватными - лишняя трата времени. все равно у всех полный доступ 3. В общем в С++, есть устоявшаяся практика, делать глобальный оператор<<, и объявлять его дружественным (friend). для доступа непосредственно к приватным членам. Все остальные модификации (по крайней мере для вашего примера) - суть одно и тоже, записанное разными способами. Так зачем голову морочить себе и другим? Лучше идти обычным путем. |
|||
|
||||
| EvilsInterrupt |
|
|||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
Ввиду того что пока у меня сформировалось свое собственное мнение по поводу использования "друзей", стараюсь этого не делать Добавлено через 9 минут и 34 секунды Не совсем. Попадавшиеся мне проекты с применением набора библиотек POCO ни одного перегруженного оператора вывода\ввода. Правда это были проекты продуктов для reverse-engineer-ов и возможно это особенность мышления разработчиков. Но тем не менее не везде перегружается. К примеру в продукте компании где работаю не применяется |
|||
|
||||
| volatile |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 2107 Регистрация: 7.1.2011 Репутация: 37 Всего: 85 |
EvilsInterrupt, ну хорошо, делайте как принято у вас. Принциаиальной выгоды от какого-то определенного способа нет. Главное здесь - делать однообразно, а не придумывать каждый раз новое седло к старому велосипеду. Это сообщение отредактировал(а) volatile - 22.6.2013, 21:22 |
|||
|
||||
| EvilsInterrupt |
|
|||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
Вопрос не в том делать мне или не делать как у меня принято в компании. Вопрос в другом. Есть. Столкнулся с тем, что мне стало сложно добавить новый код. У меня класс по работе с форматом принимает ссылку в конструкторе. Это приводит к тому, что после класс заполнить данными из другого стрима уже невозможно. Сейчас приходится рефакторить, вот если бы кто подсказал ранее!!! Да в процессе рефакторинга, сначала передавал стрим с помощью boost::shared_ptr, но это оказалось излишним. Вот и хочется узнать кто как делает, чтобы уменьшить количество лишних телодвижений. |
|||
|
||||
| volatile |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 2107 Регистрация: 7.1.2011 Репутация: 37 Всего: 85 |
||||
|
||||
| mes |
|
||||
|
любитель ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 7954 Регистрация: 14.1.2006 Репутация: 144 Всего: 250 |
подсказка: в моем примере трое участников вместо двух.. нет прямой связи друзей с применением оператора.. Кстати чем так сильно отличается дружественная функция, от обычного метода ?! Добавлено @ 03:24
так вроде ж: http://forum.vingrad.ru/forum/topic-336639/unread-1.html Это сообщение отредактировал(а) mes - 23.6.2013, 03:25 |
||||
|
|||||
| EvilsInterrupt |
|
||||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
Это был формат PE, а я сейчас ковыряюсь с другим форматом, хоть и не хочется, но трудящиеся просят )
Дело в том, что в public попадает то что очень редко будет меняться, а в привате автор кода имеет право переколбасить в любой момент наплевав на любое мнение. Если же сделать дружественную функцию, то в ней возникнет соблазн заюзать "по-быстрому" вон-ту функцию, но возникает лишняя зависимость, которую приходится учитывать если автор кода поменял сигнатуру исопользуемой функции или вообще удалил. Все-таки паблик на то и паблик, чтобы сказать пользователям класса "Вот методы, которые постараюсь менять в самых экстренных случаях" |
||||
|
|||||
| volatile |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 2107 Регистрация: 7.1.2011 Репутация: 37 Всего: 85 |
||||
|
||||
| EvilsInterrupt |
|
|||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
Тут Вы правы из-за желания написать хорошо иногда вхожу в ступор, вместо того чтобы просто написать и посмотреть как оно на практике будет выглядеть. volatile, Попробую показать свое понимание дружеских функций, возможно вы увидите ошибки в рассуждениях и укажите на них. Сразу скажу, что опыт применения дружеских функций маленький и поэтому вполне возможно что вы все-таки ошибки увидите! Далее следуют мои мысли, а не цитаты из учебников, поэтому не следует говорить "где же вы такого по-набирались?". Чисто технически пользовательский код не может видеть приватную часть другого класса. Но это можно организовать объявив в объявлении класса эту функцию дружественной. Получается вроде входит в namespace класса и в тоже время видит все его внутреннее состояние словно это метод класса. Однако при реализации такой функции нужны лишь часть а не весь функционал класса и получается своего рода "дыра". Во время написании такой функции программист отчетливо понимает как и что он пишет и зачем. Но проходит время, к этой функции обращается уже другой программист, который не знает всех деталей и нюансов класса. Который между прочим за это время тоже мог измениться. Для решения задачи из-за чего пришлось обратиться к модификации этой дружественной функции программист может обратиться к тому функционалу класса, который лучше всего не трогать! Да, спустя время юнит-тесты, интеграционные тесты или гневный пользователь все-таки ему скажет о неправильности его действий, но ведь это время! По этой причине я делю код на интерфейсный и детали. Детали я изменяю как хочу и когда хочу, никто мне в этом ни указ, главное чтобы работало! А вот интерфейсный стараюсь не менять, иначе пользовательский код придется менять. Очень жалею что нету C++ конструкции, чтобы пометить какой-либо интерфейсный код меткой "depricated", разве что pragma для MSVS но это не портабельно! Т.е. мое отношение к дружественным функциям такое, что лучше избегать их, иначе кто-то заюзает детали класса, а тебе потом собирать "артефакты" или помогать пофиксить код. |
|||
|
||||
| mes |
|
||||||||||||
|
любитель ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 7954 Регистрация: 14.1.2006 Репутация: 144 Всего: 250 |
и
все это относится и к методу...
1. операторы относятся тоже к интерфейсу 2. где тут проблема с дружественными функциями ?! 3. оператор << может быть вполне и не дружественным.. вместо подобных рассуждений, думаю не плохо было бы задать себе вопрос, в чем же прелесть дружественных функций, и сразу станет понятно когда стоит ич применять, а когда нет.. Добавлено через 2 минуты и 31 секунду
конечно, если от их применения ни красоты, ни эффективности не добавляется... Добавлено через 4 минуты и 14 секунд
EvilsInterrupt, или сделайте метод вывода в поток, и заюзайте его в операторе - будут и овцы сыты и волки целы- Добавлено через 9 минут и 32 секунды
1. public методы могут быть у private-классов.. 2. интерфейс бывает и protected, и на него распространяются те же требования.. Добавлено через 11 минут и 48 секунд это вобще отдельная тема, гораздо шире, чем публик-методы.. и кстати дружественные функции как раз и придуманы для уменьшения зависимостей и укрепления интерфейса |
||||||||||||
|
|||||||||||||
| EvilsInterrupt |
|
|||
|
Executables research ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1019 Регистрация: 14.7.2007 Где: Железнодорожный, МО, Россия Репутация: 2 Всего: 9 |
Эти рассуждения как раз и были высказаны, чтобы ответить на этот вопрос. Я не однократно задавался этим вопросом и не понимаю в чем их крутость? Однако имеется только одно пояснение, которое я нашел зачем эти дружественные были введены в язык и оно написано в книге Страуструпа про Дизайн и Эволюцию языка. Ок, спрошу у Вас: как вы понимаете в чем прелесть возможности объявить функцию\метод дружественной? |
|||
|
||||
| mes |
|
|||
|
любитель ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 7954 Регистрация: 14.1.2006 Репутация: 144 Всего: 250 |
||||
|
||||
![]()
|
| Правила форума "С++:Общие вопросы" | |
|
|
Добро пожаловать!
Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn |
| 0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) | |
| 0 Пользователей: | |
| « Предыдущая тема | C/C++: Общие вопросы | Следующая тема » |
|
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |