2013-06-05 3 views
8

Согласно Effective Java:Почему классы, предназначенные для наследования, должны редко реализовывать интерфейс Serializble?

Классы, предназначенные для наследования должны редко осуществлять Serializable, и интерфейсы должны редко продлить его.

В чем причина этого заявления? Другими словами, каковы были бы проблемы, если бы они реализовали интерфейс Serializable?

+4

Мое воспоминание может быть ржавым, но если я прав, Джош Блох объяснил рассуждения в том же пункте. –

+0

@ ZiyaoWei Нет, он этого не делает. – Geek

+0

Я предполагаю, что это означало бы, что все классы, которые являются неотъемлемыми от этого, могут быть сериализованы (что необязательно обязательно верно) –

ответ

7

Следующее предложение в том же пункте это говорит:

Классы, предназначенные для наследования (пункт 17) следует редко реализовать Serializable и интерфейсы должны редко продлить его. Нарушение этого правила ставит значительную нагрузку на всех, кто расширяет класс или реализует интерфейс. Бывают случаи, когда необходимо нарушать правило. Например, если класс или интерфейс существуют прежде всего для участия в структуре, которая требует от всех участников реализации Serializable, то для класса или интерфейса имеет смысл реализовать или расширить Serializable.

Поскольку я не хочу, чтобы Джош был на моем хвосте для нарушения авторских прав (как бы это ни было холодно), я бы не копировал весь элемент в этом ответе. Достаточно сказать, что аргументация этого объясняется в остальной части предмета.

EDIT: Джош перечисляет ряд затрат на внедрение Serializable. Если интерфейс/суперкласс реализует его, затраты будут вынуждены пересекать расширяющиеся классы.

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

...

Вторая стоимость реализации Serializable является то, что он увеличивает вероятность ошибок и дыр в безопасности. ...

Третья стоимость внедрения Serializable заключается в том, что она увеличивает нагрузку на тестирование, связанную с выпуском новой версии класса.

+1

Как смелая строка отвечает на мой вопрос? Почему нарушение этого правила налагает существенное бремя? Я ищу какое-то объяснение ... – Geek

+0

Поскольку класс внедрения должен быть уверен, что любые классы, которые они используют, должны быть сериализуемыми или определенными как переходные. –

+0

@ Ziyao +1 для редактирования. – Geek

0

Всех подтипов сериализуемого класса сами сериализации, как указано here .so Если вы собираетесь сериализовать класс предназначен для наследования, вы должны знать, нужны ли все суб-классы, чтобы быть serialized.Otherwise вы можете сериализовать нужный подпункт только классы.

7

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

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

+0

+1 для примера добавления несериализуемых полей в подклассы. – Geek

+0

+1 для ясности ответа. – eternay

+0

+1, но я должен сказать, что приведенные причины Блоха не имеют смысла. В этом нет «сил»: это «значительное бремя» относится только к будущим исполнителям *, если класс будет сериализован *, и в этом случае «существенное бремя» неизбежно и где именно «реализует Serializable» не имеет к этому никакого отношения. – EJP

Смежные вопросы