Подтвердить что ты не робот

Всегда ли хранятся статические методы в памяти?

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

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

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

То, что я не получаю, это то, что они утверждают, статические методы всегда хранятся в памяти и заполняют основное использование памяти. Итак, если вы используете 100 статических методов в своей программе, при запуске программы все методы загружаются в память и без необходимости заполняют память. Дальнейшие более статические методы увеличивают риск нехватки памяти.

Это правда?

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

4b9b3361

Ответ 1

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

Методы занимают пространство для их машинного кода, фактического кода, который выполняет процессор. И таблица, которая описывает, как метод хранит объекты, что помогает сборщику мусора обнаруживать корни объектов, хранящиеся в локальных переменных и регистры процессора. Это пространство взято из "кучи загрузчика", внутренней структуры данных, создаваемой средой CLR, которая связана с AppDomain. Случается только один раз, когда метод сначала выполняется, точно в срок. Для освобождения этого пространства требуется разгрузка этого приложения. Статические переменные также выделяются в куче загрузчика.

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

Ответ 2

Очень неудобно создавать новый экземпляр класса только для вызова метода. Но вот как они это делают прямо сейчас

Они смехотворны, чтобы быть тупыми.

Как отмечал комментатор Groo, на собственном скомпилированном уровне метод экземпляра даже не отличается от статического метода. Это просто, что неявный параметр передается методу экземпляра, тогда как со статическим методом "то, что вы видите, это то, что вы получаете".

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

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


И, помимо всего прочего, пусть на мгновение ваши коллеги будут правы. Что бы вы получили? Любая измеримая разница в производительности? Сомнительно. Давайте посмотрим правде в глаза: управляемый код, и особенно С#, может скрыть от нас какое-то количество деталей реализации, снижающих производительность. Основная причина, по которой мы используем управляемый кодовый язык, такой как С#, состоит в том, что мы получаем так много производительности и правильности кода, что эти возможные неэффективности стоят того. В большинстве случаев, особенно на современных компьютерах, они практически невидимы.

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