Точно, что происходит когда Foo. SomeCheck () называют в классе Панели? Экземпляр Foo создается для вызова SomeCheck ()? Если так, этот экземпляр хранится на "куче", и это когда-либо собирается посредством сборки "мусора"?
public class Foo() {
public static bool SomeCheck() {
return true;
}
}
public class Bar() {
public void SomeMethod() {
// what happens when we access Foo to call SomeCheck?
if (Foo.SomeCheck()) {
//do something
}
}
}
Статические методы отличаются от методов экземпляра тем, что ни один экземпляр класса, к которому они принадлежат, не должен быть создан для их вызова. Когда вы вызываете статический метод, вы фактически делаете вызов, используя имя типа , а не экземпляр типа, что должно укрепить идею о том, что статические методы не вызываются в экземплярах. Это требует повторения и подчеркивания : Для вызова общедоступного статического метода этого класса не требуется экземпляр класса.
Ваш пример неверен, но предположительно строка: if (Foo.SomeCheck ())
вызывает статический метод SomeCheck
, используя имя тип: Foo
- не экземпляр. Bar, однако, должен быть создан для того, чтобы сделать этот вызов - , однако в вашем примере у вас нет правильно сформированного экземпляра Bar
. Код обычно должен существовать внутри метода (или инициализатора члена), которого здесь нет.
Чтобы ответить на другие части вашего вопроса.Предполагая, что рассматриваемый код является частью метода экземпляра, что-то должно создать экземпляр Bar
- и вызвать этот метод. Это нечто должно было бы создать или иным образом получить экземпляр Bar
. Ссылочные типы всегда будут создаваться в куче, но здесь это не имеет значения.
Что касается сборки мусора, вам обычно не стоит об этом беспокоиться. Среда выполнения .NET гарантирует очистку экземпляров, на которые не ссылаются ни один корневой объект в вашей программе. Корни обычно представляют собой экземпляры, которые находятся где-то в стеке вызовов или на которые ссылаются статические члены того или иного типа. Поскольку мы не видим здесь кода, который создает или ссылается на Bar
, невозможно сказать , когда он будет собран. Например, если Bar
является одноэлементным и хранится где-то в статической переменной, он может существовать очень долго - возможно, все время существования программы. Вы не можете точно знать, не увидев всего кода, который манипулирует и управляет Bar
.
Я настоятельно рекомендую прочитать следующую статью:
В ней объясняется, как среда выполнения .NET работает на на низком уровне и объясняет внутренние нюансы, такие как кучи загрузчика и как работают статические классы / члены. Технически говоря, существует начальная реализация «статического экземпляра» статических членов класса.Однако это инициирование обрабатывается средой выполнения иначе, чем оно обрабатывается для экземпляров класса. Статические классы хранятся в кучах загрузчика, которые не управляются сборщиком мусора. Куча загрузчика распределяется и увеличивается статично и не уплотняется. Эта статья отлично читается и должна дать вам полное представление о том, как работает среда CLR.
(ПРИМЕЧАНИЕ: я не уверен, насколько эта статья актуальна для .NET 4. Я знаю, что в .NET 4 были изменения сборщика мусора, однако я не уверен, сколько фундаментальных изменений в среде выполнения. DLR и другие функции могут в некоторой степени отличаться от объяснения в приведенной выше статье.)
Это зависит от реализации SomeMethod
. Этот метод нужно будет вызывать откуда-то, предположительно из класса «драйвера», который будет создавать экземпляр Bar и вызывать SomeMethod
. Например:
public class Driver
{
public static void Main()
{
Bar bar = new Bar();
bar.SomeMethod();
}
}
Учитывая вашу текущую реализацию SomeMethod
, да, вам придется создать его экземпляр.
Однако, пока SomeMethod
вызывает только другой статический метод, мы могли бы сделать make it статическим. В этом случае вам не нужно создавать экземпляр Bar для вызова метода. то есть
public class Driver
{
public static void Main()
{
Bar.SomeMethod();
}
}
Foo
не нужно инстанцировать, также он не будет инстанцирован при вызове статического метода SomeCheck
, в результате вы получите значение, возвращаемое самим методом, а не экземпляр класса.
Пожалуйста, посмотрите эти ссылки для более подробной информации:
Надеюсь, это поможет! =)
public class Manipulate
{
public static int Main(string[] args) {
Bar bar = new Bar();
bar.BarFoo();
Console.ReadKey();
return 0;
}
}
public class Foo {
public static bool SomeCheck() {
return true;
}
}
public class Bar {
// what happens when we access Foo to call SomeCheck?
public void BarFoo() {
if (Foo.SomeCheck()) {
Console.WriteLine("Hello am true");
}
}
}
Да, вам нужно создать экземпляр Bar, но не для класса Foo, поскольку это статический метод. Единственная разница в том, что статические методы вызываются на уровне класса (время компиляции), а не на уровне объекта (время выполнения), поэтому вам не нужно инстанцировать класс Foo.