Classes static e membros de classes static (Guia de Programação em C#)
Uma classe estática é basicamente a mesma coisa que uma classe não estática, mas há uma diferença: uma classe estática não pode ser instanciada. Em outras palavras, não é possível usar o operador novo para criar uma variável do tipo de classe. Como não há variável de instância, acesse os membros de uma classe estática usando o próprio nome da classe. Por exemplo, se houver uma classe estática chamada UtilityClass
com um método público chamado MethodA
, chame o método, como mostra o exemplo a seguir:
UtilityClass.MethodA();
Uma classe estática pode ser usada como um contêiner conveniente para conjuntos de métodos que operam apenas em parâmetros de entrada e não precisam obter ou definir nenhum campo de instância interno. Por exemplo, na biblioteca de classes .NET, a classe estática System.Math contém métodos que executam operações matemáticas, sem a necessidade de armazenar ou recuperar dados que são exclusivos de uma determinada instância da classe Math. Ou seja, você aplica os membros da classe especificando o nome de classe e o nome do método, conforme mostrado no exemplo a seguir.
double dub = -3.14;
Console.WriteLine(Math.Abs(dub));
Console.WriteLine(Math.Floor(dub));
Console.WriteLine(Math.Round(Math.Abs(dub)));
// Output:
// 3.14
// -4
// 3
Como ocorre com todos os tipos de classe, o runtime do .NET carrega as informações de tipo de uma classe estática quando o programa que faz referência à classe é carregado. O programa não pode especificar exatamente quando a classe será carregada. Entretanto, é garantido que ela seja carregada e que seus campos sejam inicializados e que seu construtor estático seja chamado antes que a classe seja referenciada pela primeira vez em seu programa. Um construtor estático é chamado apenas uma vez e uma classe estática permanece na memória pelo tempo de vida do domínio do aplicativo em que seu programa reside.
Observação
Para criar uma classe não estática que permite que apenas uma instância de si mesma seja criada, consulte Implementando singleton no C#.
A lista a seguir fornece os principais recursos de uma classe estática:
Contém apenas membros estáticos.
Não pode ser instanciada.
É lacrada.
Não pode conter construtores de instâncias.
Criar uma classe estática é, portanto, basicamente o mesmo que criar uma classe que contém apenas membros estáticos e um construtor particular. Um construtor particular impede que a classe seja instanciada. A vantagem de usar uma classe estática é que o compilador pode verificar se nenhum membro de instância foi adicionado acidentalmente. O compilador garante que as instâncias dessa classe não podem ser criadas.
As classes estáticas são seladas e, portanto, não podem ser herdadas. Elas não podem herdar de nenhuma classe ou interface, exceto Object. As classes estáticas não podem conter um construtor de instâncias. No entanto, eles podem conter um construtor estático. Classes não estáticas também devem definir um construtor estático se a classe contiver membros estáticos que exigem inicialização não trivial. Para obter mais informações, consulte Construtores estáticos.
Exemplo
Aqui está um exemplo de uma classe estática que contém dois métodos que convertem a temperatura de Celsius para Fahrenheit e de Fahrenheit para Celsius:
public static class TemperatureConverter
{
public static double CelsiusToFahrenheit(string temperatureCelsius)
{
// Convert argument to double for calculations.
double celsius = Double.Parse(temperatureCelsius);
// Convert Celsius to Fahrenheit.
double fahrenheit = (celsius * 9 / 5) + 32;
return fahrenheit;
}
public static double FahrenheitToCelsius(string temperatureFahrenheit)
{
// Convert argument to double for calculations.
double fahrenheit = Double.Parse(temperatureFahrenheit);
// Convert Fahrenheit to Celsius.
double celsius = (fahrenheit - 32) * 5 / 9;
return celsius;
}
}
class TestTemperatureConverter
{
static void Main()
{
Console.WriteLine("Please select the convertor direction");
Console.WriteLine("1. From Celsius to Fahrenheit.");
Console.WriteLine("2. From Fahrenheit to Celsius.");
Console.Write(":");
string? selection = Console.ReadLine();
double F, C = 0;
switch (selection)
{
case "1":
Console.Write("Please enter the Celsius temperature: ");
F = TemperatureConverter.CelsiusToFahrenheit(Console.ReadLine() ?? "0");
Console.WriteLine("Temperature in Fahrenheit: {0:F2}", F);
break;
case "2":
Console.Write("Please enter the Fahrenheit temperature: ");
C = TemperatureConverter.FahrenheitToCelsius(Console.ReadLine() ?? "0");
Console.WriteLine("Temperature in Celsius: {0:F2}", C);
break;
default:
Console.WriteLine("Please select a convertor.");
break;
}
// Keep the console window open in debug mode.
Console.WriteLine("Press any key to exit.");
Console.ReadKey();
}
}
/* Example Output:
Please select the convertor direction
1. From Celsius to Fahrenheit.
2. From Fahrenheit to Celsius.
:2
Please enter the Fahrenheit temperature: 20
Temperature in Celsius: -6.67
Press any key to exit.
*/
Membros Estáticos
Uma classe não estática não pode conter métodos, campos, propriedades ou eventos estáticos. O membro estático pode ser chamado em uma classe mesmo que não exista nenhuma instância da classe. O membro estático sempre é acessado pelo nome de classe, não pelo nome da instância. Existe apenas uma cópia de um membro estático, independentemente de quantas instâncias da classe forem criadas. Os métodos e propriedades estáticos não podem acessar campos e eventos não estáticos no tipo que os contém e não podem acessar uma variável de instância de qualquer objeto, a menos que ela seja explicitamente passada em um parâmetro de método.
É mais comum declarar uma classe não estática com alguns membros estáticos do que declarar uma classe inteira como estática. Dois usos comuns de campos estáticos são manter uma contagem do número de objetos que são instanciados ou armazenar um valor que deve ser compartilhado entre todas as instâncias.
Métodos estáticos podem ser sobrecarregados, mas não substituídos, porque pertencem à classe e não a qualquer instância da classe.
Embora um campo não possa ser declarado como static const
, um campo const é essencialmente estático em seu comportamento. Ele pertence ao tipo e não a instâncias do tipo. Portanto, os campos const
podem ser acessados usando a mesma notação ClassName.MemberName
usada para campos estáticos. Nenhuma instância de objeto é necessária.
O C# não dá suporte a variáveis locais estáticas (ou seja, variáveis que são declaradas no escopo do método).
Você declara membros de classe estática usando a palavra-chave static
antes do tipo de retorno do membro, conforme mostrado no exemplo a seguir:
public class Automobile
{
public static int NumberOfWheels = 4;
public static int SizeOfGasTank
{
get
{
return 15;
}
}
public static void Drive() { }
public static event EventType? RunOutOfGas;
// Other non-static fields and properties...
}
Os membros estáticos são inicializados antes que o membro estático seja acessado pela primeira vez e antes que o construtor estático, se houver um, seja chamado. Para acessar um membro de classe estática, use o nome da classe em vez de um nome de variável para especificar o local do membro, conforme mostrado no exemplo a seguir:
Automobile.Drive();
int i = Automobile.NumberOfWheels;
Se sua classe contiver campos estáticos, forneça um construtor estático que os inicializa quando a classe é carregada.
Uma chamada a um método estático gera uma instrução de chamada na linguagem intermediária comum (CIL), enquanto uma chamada a um método de instância gera uma instrução callvirt
, que também verifica se há referências a objetos nulos. Entretanto, na maioria das vezes, a diferença de desempenho entre os dois não é significativa.
Especificação da Linguagem C#
Para saber mais, confira Classes estáticas, Membros estáticos e de instância e Construtores estáticos na Especificação da linguagem C#. A especificação da linguagem é a fonte definitiva para a sintaxe e o uso de C#.