ReSharper жалуется, когда метод может быть статическим, но это не так.

Почему ReSharper жалуется, когда метод может стать статическим, но не стал?

Это потому, что создается только один экземпляр статического метода (по типу) и, таким образом, экономится производительность?


person Andreas Grech    schedule 26.04.2009    source источник
comment
Есть очень похожий вопрос для java и параметров компилятора eclipse stackoverflow.com/questions/11240178/ разные языки, те же вопросы; =)   -  person Samuel Rossille    schedule 13.07.2012
comment
Имя этой инспекции - Член может быть статическим (совместно используемым), и у него есть два варианта частной доступности и не частной доступности. (В ReSharper 7.1.) Он указан в ReSharper ›Параметры› Проверка кода ›Уровень проверки› Все ›Общие методы и улучшения кода.   -  person Rory O'Kane    schedule 23.05.2013
comment
Пример снимка экрана меню действий для этой проверки ReSharper. (Хотя это для кода VB.NET.)   -  person Rory O'Kane    schedule 23.05.2013


Ответы (8)


Я считаю этот комментарий очень полезным, поскольку он указывает на две важные вещи:

  1. Это заставляет меня задаться вопросом, действительно ли рассматриваемый метод должен быть частью типа или нет. Поскольку он не использует никаких данных экземпляра, вы должны хотя бы подумать, можно ли его переместить в свой собственный тип. Является ли это неотъемлемой частью типа или действительно служебным методом общего назначения?

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

person Brian Rasmussen    schedule 26.04.2009
comment
Хороший ответ - дело не только в производительности. Resharper также дает вам некоторые отзывы о дизайне. - person serg10; 27.04.2009

Из документации FxCop для того же предупреждения (выделено мной):

«Члены, которые не имеют доступа к данным экземпляра или вызывают методы экземпляра, могут быть помечены как статические (общие в Visual Basic). После того, как вы отметите методы как статические, компилятор будет передавать этим членам невиртуальные сайты вызовов. Испускание невиртуального вызова сайты будут предотвращать проверку во время выполнения для каждого вызова, который гарантирует, что текущий указатель объекта не равен нулю. Это может привести к измеримому увеличению производительности для кода, чувствительного к производительности. В некоторых случаях невозможность доступа к текущему объекту экземпляр представляет собой проблему с правильностью. "

person itowlson    schedule 26.04.2009
comment
Это правда, но на самом деле прирост производительности не такой большой. Я выключаю это предупреждение. Раздражает, пока вы в разработке, что ReSharper хочет сделать все статичным. - person Chad Grant; 26.04.2009
comment
Это правда, но игнорирует тот факт, что вам НЕ нужно создавать объект для доступа к методу ... Если вам не нужен экземпляр по какой-либо другой причине, отсутствие необходимости создавать объект - это гораздо больший прирост производительности . - person Charles Bretana; 26.04.2009
comment
Согласитесь, прирост производительности в целом довольно незначительный (незначительный для большинства нетривиальных методов). Причина правильности, как правило, вызывает большее беспокойство - если метод не специфичен для экземпляра, пометка его статическим дает понять, что это сделано намеренно, и если метод предназначен для экземпляр, то предупреждение сообщает вам, что вы допустили ошибку в реализации. - person itowlson; 26.04.2009
comment
@Chad: resharper не «хочет» делать вещи статичными; Он просто отмечает, что его все еще можно сделать статичным; относитесь к нему как к маркеру TODO, если хотите. Если вы действительно утверждаете, что «хочет сделать все статическим» ... я бы подумал, что в вашем коде есть серьезные проблемы с дизайном. - person sehe; 28.08.2011
comment
@sehe хочет / рекомендовать ... как бы вы ни хотели интерпретировать это слово, Reshaper ворчит на это. Я не знаю, что вы взяли из моего комментария, который заставляет вас думать, что я лично сводлю СВОЙ код с ума от статичности. Агрессивно сильно? - person Chad Grant; 26.01.2012
comment
@ChadGrant: Ха-ха, ура - очень поздно :) Обратите внимание, я выделил курсивом слово, чтобы выделить гиперболу. Так что прочтите еще раз: Если .... действительно ... все ... Я подумал бы [ ...]. Другими словами, я в шутку указывал на ненужное преувеличение. - person sehe; 26.01.2012

Здесь очень хорошие дебаты по этому вопросу (SO) . Я нахожусь в лагере «если-это-можно-сделать-статичным-сделать-статичным». Я считаю, что это связано с тем, что нужно иметь метод экземпляра, который не использует никаких данных экземпляра. Действительно ли это метод экземпляра в этом случае или это действительно метод класса?

person JP Alioto    schedule 27.04.2009

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

Также ваш вопрос, как это написано

«... создается только один экземпляр статического метода (по типу) ...»

подразумевает, что для метода экземпляра код метода повторяется для каждого экземпляра создаваемого класса. Это неправда. Независимо от того, сколько экземпляров вы создаете для любого типа, код методов загружается в память только один раз. Объект, хранящийся в куче для каждого экземпляра, хранит только «Состояние» типа (нестатические поля и несколько разных переменных отслеживания).

person Charles Bretana    schedule 26.04.2009

Это не жалоба, это просто совет.

person FFire    schedule 26.04.2009

Вам не нужно помещать "this" в стек функции для статического метода. Это еще одна причина, по которой он дешевле.

person Chris Farmer    schedule 26.04.2009

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

Еще один изящный трюк со статикой в ​​ReSharper - сделать набор связанных методов статическим с помощью рефакторинга «Сделать метод статическим». Это переместит некоторые зависимости в параметры метода. Когда вы позже посмотрите на этот набор методов, вы можете обнаружить, что все они обращаются к определенному объекту определенного типа. Затем вы можете использовать рефакторинг «Сделать метод нестатическим» и указать этот объект как новый указатель this. Это перемещает ваш метод в другой класс.

Из этого:

internal class ClassA
{
    public ClassB Property { get; set; }

    public int Method()
    {
        var classB = Property;
        return classB.Property1 + classB.Property2;
    }
}

internal class ClassB
{
    public int Property1 { get; set; }
    public int Property2 { get; set; }
}

к этому:

    public static int Method(ClassB property)
    {
        var classB = property;
        return classB.Property1 + classB.Property2;
    }

к этому:

internal class ClassA
{
    public ClassB Property { get; set; }
}

internal class ClassB
{
    public int Property1 { get; set; }
    public int Property2 { get; set; }

    public int Method()
    {
        return Property1 + Property2;
    }
}
person John Saunders    schedule 27.04.2009
comment
Это означает, что его можно легко переместить в другой класс как статический член. Это также означает, что вы пишете процедурный, а не объектно-ориентированный код, а это плохо. - person Evren Kuzucuoglu; 14.03.2011
comment
@GFK: может быть, а может и нет. Как только он станет статическим, вы можете переместить его в другой класс и, возможно, сделать его членом экземпляра этого класса. - person John Saunders; 14.03.2011

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

person Thibault Deheurles    schedule 10.02.2015