Рефакторинг большого метода в.NET

Если у меня есть большой метод.NET, я хочу знать - ли это хорошая практика для разделения его на несколько методов или нет. Мои проблемы: 1 - там какая-либо точка, создающая метод, если это только назовут однажды?
2 - Если я называю закрытый метод из своего класса, я пытаюсь не использовать переменные экземпляра. Эта хорошая или плохая практика? Например:

var a, b;
public void TestMe
{
   FirstTest(a,b);
}
private void FirstTest(paramA, paramB)
{
         //code here with passed in parameters
}

//instead of:
private void FirstTest()
{
      //code here with instance variables a,b
}  

править: замена, глобальная с экземпляром

8
задан MC. 9 March 2010 в 20:34
поделиться

4 ответа

1 - Есть ли смысл создавать метод , если он будет вызываться только один раз?

Да, для этого есть много причин. Читаемость, пожалуй, самое главное. Если вы можете сделать метод более читабельным и поддерживаемым, разбив его на части, то обязательно сделайте это.

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

2 - Если я вызываю частный метод из своего класса, я стараюсь не использовать переменные экземпляра . Это хорошая или плохая практика?

Обычно, чем меньше область видимости переменной, тем лучше. Как и вы, я стараюсь по возможности использовать параметры. Если у метода есть ссылки только на свои собственные параметры, тогда становится намного проще рассуждать о методе, проверять его правильность и правильно использовать. (И если метод может делать это и не изменять какое-либо состояние, то это дает вам лот преимуществ обслуживания.)

Если цель метода лучше всего достигается за счет манипулирования полями объекта, то это вполне приемлемо и во многих случаях невозможно. Но, как вы указываете, это особенно верно в отношении общедоступных методов. При рефакторинге большого метода в более мелкие я редко, если вообще когда-либо, буду обращаться к полям-членам непосредственно в новых методах. В основном это делается для того, чтобы было легче рассуждать о поведении программы.

При таком рефакторинге убедитесь, что вы пометили новые методы как static , если они не обращаются ни к каким полям. Это сделает намерение явным.

5
ответ дан 5 December 2019 в 08:51
поделиться

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

Что касается второго вопроса, как указывает @Jason, вы используете переменные экземпляра, а не глобальные переменные в своем классе. Я бы сказал, какая практика предпочтительнее, зависит от контекста метода. Конечно, если метод можно повторно использовать во многих контекстах, только некоторые из которых работают с переменными экземпляра, его следует параметризовать. Если вы когда-либо используете только переменные экземпляра, вы можете отказаться от параметров и выполнить рефакторинг, если это потребуется позже для удобства использования.

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

9
ответ дан 5 December 2019 в 08:51
поделиться
  1. Если часть кода будет вызываться только один раз, то, скорее всего, нет причин для создания метода в первую очередь. ОДНАКО, с учетом сказанного, если это частный метод и он используется как отдельная часть функциональности (отдельная проблема), тогда было бы неплохо разделить его. Вы бы хотели сделать это, чтобы избежать единственного огромного метода. Например, если я выполняю поиск только один раз в фрагменте кода, я все равно хочу разделить этот поиск, потому что поиск - это отдельная часть функциональности. (Это очень плохой пример. Если у кого-то есть лучший вариант, пожалуйста, не стесняйтесь редактировать.

  2. Переменная не является НАСТОЯЩИМ глобальной, если она не доступна во всей системе. С учетом сказанного, я настоятельно рекомендую избегать глобального переменные, потому что это очень затрудняет отладку и работу с кодом, потому что переменные имеют чрезвычайно большую область видимости. Вместо этого я бы сосредоточился на наличии более локализованных переменных и передаче переменных, которые могут понадобиться функции / методу, и возвращении данных, которые вызывающий функция ожидает. Таким образом вы сохраните свои данные более локализованными, и, в конечном итоге, код будет легче читать и управлять. Это не относится к частным или общедоступным методам.

1
ответ дан 5 December 2019 в 08:51
поделиться

Цитата из Clean Code (отличная книга), метод должен делать одно и только одно. Если вы выполняете несколько действий в методе, это, вероятно, означает, что вам нужно выделить эту логику в отдельный метод. Это также значительно упрощает отслеживание кода. Итак, я бы сказал

Вопрос 1: Да, разбейте (разделение интересов).

Вопрос 2: В общем, я считаю, что иметь глобальные переменные - плохая практика, если только вам не абсолютно необходимо . Что касается общего вопроса об использовании частной собственности (переменной экземпляра) отдельно от общедоступного геттера, я не вижу никаких преимуществ от использования геттера. Например, рассмотрим:

function someFunc() {
  anotherFunc(this.a, this.b);
}

function anotherFunc(int paramA, int paramB) {
  //do stuff with paramA and paramB
}

против

function someFunc() {
  anotherFunc();
}

function anotherFunc() {
  //do stuff with this.a and this.b
}

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

4
ответ дан 5 December 2019 в 08:51
поделиться
Другие вопросы по тегам:

Похожие вопросы: