Одна вещь, с которой я столкнулся несколько раз, - это класс сервиса (например, сервис JBoss), который стал слишком большим из-за вспомогательных внутренних классов. Я еще не нашел хороший способ вырваться из класса. Этими помощниками обычно являются темы. Вот пример:
/** Asset service keeps track of the metadata about assets that live on other
* systems. Complications include the fact the assets have a lifecycle and their
* physical representation lives on other systems that have to be polled to find
* out if the Asset is still there. */
public class AssetService
{
//...various private variables
//...various methods
public AssetService()
{
Job pollerJob = jobService.schedule( new AssetPoller() );
Job lifeCycleJob = jobService.schedule( AssetLifecycleMonitor() );
}
class AssetPoller
{
public void run()
{
// contact remote systems and update this service's private variables that
// track the assets.
}
}
class AssetLifecycleMonitor
{
public void run()
{
// look for assets that have meet criteria for a lifecycle shift
// and update this service's private variables as relevant.
}
}
}
Итак, что может произойти, если у меня есть пара помощников, и они вообще сложные, если общий файл класса может стать действительно большим. Мне нравятся внутренние классы в том смысле, что они ясно показывают, что классы полностью принадлежат сервису и существуют только для того, чтобы помочь этому сервису. Я попытался разбить классы и передать родительский сервис в качестве ссылки, что в основном работает, но мне не нравятся следующие вещи:
Я заканчиваю тем, что выставляю методы доступа уровня пакета, чтобы разбитые классы могли получить доступ к переменным, тогда как раньше я вообще не выставлял сеттеры, поскольку внутренние классы имели прямой доступ.
Плюс, все становится немного более объемным, поскольку я постоянно вызываю методы доступа, а не лежащие в их основе переменные. Незначительная гнида, само собой разумеющееся.
Удобные методы (например, checkAssetIsValid () или некоторые другие) теперь нуждаются в представлении на уровне пакета, чтобы вспомогательные классы могли вызывать их, где, как и прежде, как внутренние классы, они могут быть закрытыми.
Хуже того, мне нужно передать класс реализации службы конструкторам вспомогательных классов, поскольку я не хочу показывать эти методы-помощники в интерфейсе, который реализует служба, потому что это заставляет их быть открытыми. Это может создать некоторые проблемы с модульным тестом / издевательством.
Хуже того, любая синхронизация, которую я хотел сделать, просачивается через какой-то внешний удобный метод (например, lockDownAssets () во время обновления программы опроса). Раньше внутренние классы имели доступ к закрытым замкам.
Таким образом, короче говоря, разделение классов теряет некоторую инкапсуляцию, которая мне нравится. Но если оставить их, это может привести к большим файлам Java. Я еще не нашел хороший способ справиться с этим. В C ++ было понятие «друзья», которое я редко пропускал, но на самом деле помогло бы в этом случае.
Мысли