Eu venho de C ++ e encontro um comportamento muito diferente entre ponteiros em C ++ e C #.
Surpreendentemente, acho que esse código compila ... E até ... Funciona perfeitamente.
class C
{
private readonly int x = 0;
unsafe public void Edit()
{
fixed (int* p = &x)
{
*p = x + 1;
}
Console.WriteLine($"Value: {x}");
}
}
Isso me deixa muito confuso, mesmo em C ++, temos um mecanismo para proteger const
objetos ( const
em C ++ quase a mesma coisa que readonly
em C #, não const
em C #), porque não temos motivos suficientes para modificar arbitrariamente os valores const através de ponteiros.
Explorando mais, acho que não há equivalente aos ponteiros const de baixo nível do C ++ em C #, que serão algo como:
readonly int* p
em c # se tivesse um.
Então p só pode ler o objeto apontado e não pode gravar nele.
E para const
objetos, o C # proibiu as tentativas de recuperar seu endereço.
No C ++, qualquer tentativa de modificar o const
erro de compilação ou o comportamento indefinido. Em C #, não sei se existe alguma possibilidade de podermos fazer uso disso.
Então, minha pergunta é:
- Esse comportamento é realmente bem definido? Embora eu saiba em C #, não há conceito como UB em C ++
- Se sim, como devo usá-lo? Ou nunca usá-lo?
Nota: Na seção de comentários: jogar fora const
em C ++ não está relacionado a esta pergunta, porque é válido apenas quando o objeto apontado em si não é const
, caso contrário, é UB. Além disso, estou basicamente falando sobre C # e compilar o comportamento do tempo.
Você pode solicitar que eu forneça mais detalhes se não entender completamente a pergunta. Descobri que a maioria das pessoas não consegue entender isso corretamente, talvez seja minha culpa não esclarecer.