Médio C#
Permissões com Flags
Enunciado
Defina um enum [Flags] Permissao com os valores Nenhuma = 0, Ler = 1, Escrever = 2, Executar = 4. Crie um método que recebe uma combinação de permissões e imprime quais estão ativas. No Main, teste com Ler | Executar e depois remova Executar usando XOR (^).
Requisitos
- Use o atributo
[Flags]e valores que sejam potências de 2. - Implemente um método
ImprimirPermissoes(Permissao p)que verifica cada flag comHasFlag. - No
Main, combineLer | Executar, imprima, depois façap ^= Permissao.Executare imprima novamente. - A saída deve listar as permissões ativas separadamente.
Código inicial
using System;
[Flags]
enum Permissao
{
Nenhuma = 0,
Ler = 1,
Escrever = 2,
Executar = 4
}
class Program
{
static void ImprimirPermissoes(Permissao p)
{
// Implemente
}
static void Main()
{
// Teste as combinações
}
}
Saída esperada
Permissões ativas: Ler, Executar
Permissões ativas: Ler
Ver dica
Use p.HasFlag(Permissao.Ler) para verificar cada flag. Para remover, use p ^= Permissao.Executar; que desliga o bit se estiver ligado.
Mostrar solução
using System;
[Flags]
enum Permissao
{
Nenhuma = 0,
Ler = 1, // 0001
Escrever = 2, // 0010
Executar = 4 // 0100
}
class Program
{
static void ImprimirPermissoes(Permissao p)
{
Console.Write("Permissões ativas: ");
var ativas = new List<string>();
if (p.HasFlag(Permissao.Ler)) ativas.Add("Ler");
if (p.HasFlag(Permissao.Escrever)) ativas.Add("Escrever");
if (p.HasFlag(Permissao.Executar)) ativas.Add("Executar");
Console.WriteLine(string.Join(", ", ativas));
}
static void Main()
{
Permissao p = Permissao.Ler | Permissao.Executar; // combina com OR
ImprimirPermissoes(p);
p ^= Permissao.Executar; // remove Executar se estiver presente
ImprimirPermissoes(p);
}
}
Passo a passo
- Declaramos o enum com
[Flags]e valores que são potências de 2 (1, 2, 4) para que cada bit represente uma permissão independente. - O método
ImprimirPermissoescria uma lista de strings para armazenar os nomes das permissões ativas. - Usamos
p.HasFlag(Permissao.Ler)para testar se o bit correspondente está ligado; se sim, adicionamos o nome à lista. - No
Main, combinamosLereExecutarcom o operador|(OR bit a bit), resultando em 5 (0101). - Chamamos
ImprimirPermissoese vemos "Ler, Executar". - Depois,
p ^= Permissao.Executarfaz XOR com 4, desligando o bit de Executar (5 ^ 4 = 1). - Imprimimos novamente e obtemos apenas "Ler".
Por que funciona
O atributo [Flags] indica que o enum pode ser tratado como um campo de bits. Cada valor é uma potência de 2, então a combinação com | ativa múltiplos bits. HasFlag verifica se um bit específico está ligado. O XOR (^) alterna o bit: se estiver ligado, desliga; se desligado, liga. Como usamos após ter certeza de que Executar estava ligado, ele é removido.
Erros comuns
- Esquecer
[Flags]: sem o atributo, a saída deToString()pode não listar os nomes combinados corretamente, e a intenção não fica clara. - Valores não potência de 2: se usar
Ler = 1, Escrever = 2, Executar = 3, o valor 3 combina bits de Ler e Escrever, causando sobreposição. - Usar
&em vez de^para remover:p &= ~Permissao.Executartambém funciona, mas^só remove se estiver presente; se não estiver, adiciona. No contexto,^é seguro porque sabemos que está presente.
Outra forma de resolver
Usar p &= ~Permissao.Executar; para remover de forma incondicional. É preferível quando você quer garantir que a permissão esteja desligada, independentemente do estado atual.
Saída esperada
Permissões ativas: Ler, Executar
Permissões ativas: Ler