¿Cuál es el caso de uso del modificador "privado protegido"(C#7.2)?
.net access-modifiers (3)
Antes de C # 7.2 teníamos
protected internal
modificador
protected internal
.
Esto realmente significa protegido O interno, es decir, el miembro
A
es accesible para las clases secundarias y también para cualquier clase en el ensamblaje actual, incluso si esa clase no es secundaria de la clase
A
(por lo que la restricción implicada por "protegido" es relajada).
private protected
realmente significa protegido E interno.
Es decir, el miembro solo es accesible para las clases secundarias que están en el mismo ensamblado, pero no para las clases secundarias que están fuera del ensamblado (por lo que la restricción implícita en "protegido" se reduce, se vuelve aún más restrictiva).
Esto es útil si crea una jerarquía de clases en su ensamblado y no desea que ninguna clase secundaria de otros ensamblados acceda a ciertas partes de esa jerarquía.
Podemos tomar el ejemplo que Jon Skeet proporcionó en los comentarios . Supongamos que tienes clase
public class MyClass {
}
Y desea poder heredar de él solo en el ensamblado actual, pero no quiere permitir crear una instancia de esta clase directamente, excepto desde esta jerarquía de clases.
La herencia solo dentro del ensamblaje actual se puede lograr con el constructor interno
public class MyClass {
internal MyClass() {
}
}
La prevención de la creación de instancias directa, excepto dentro de la jerarquía de clases actual, se puede lograr con el constructor protegido:
public class MyClass {
protected MyClass() {
}
}
Y para obtener ambos, necesita
private protected
constructor
private protected
:
public class MyClass {
private protected MyClass() {
}
}
C # 7.2 presenta el modificador privado protegido .
Siempre he protegido el acceso a los campos con propiedades, lo que permite el acceso a través de los métodos Get / Set, ya que normalmente no quiero que el estado interno de mi objeto sea modificado por otra cosa que no sea mi propia clase.
Estoy tratando de entender por qué el equipo de lenguaje C # ha agregado esta función. Después de una búsqueda exhaustiva en Google, y de leer y ver los medios de comunicación ''novedades'' (he visto el comunicado de prensa , los details y el video de Mads Torgerson ), todavía no soy más sabio.
Para mí, esto parece permitir que un desarrollador rompa el principio de sustitución de Liskov, pero esto puede deberse a que no entiendo por qué esta característica ahora existe.
Entiendo cómo se puede usar, pero no por qué. ¿Alguien puede proporcionar un ejemplo de uso del mundo real en lugar de uno artificial en los documentos de MSDN?
Para los modificadores de acceso de dos palabras tengo este concepto: el primer descriptor de acceso está relacionado con otro conjunto, el segundo con el conjunto en el que se definió.
interno protegido
-
protegido en otra asamblea: accesible solo en las clases secundarias.
-
interno en la asamblea actual: accesible para todos en la asamblea actual.
privado protegido
- privado en otra asamblea: no es accesible.
- protegido en el ensamblaje actual: accesible solo en las clases secundarias.
Supongamos que tiene una clase interna llamada
SomeHelper
que desea usar como parte de la implementación de una clase base abstracta pública:
public abstract class Test
{
// Won''t compile because SomeHelper is internal.
protected SomeHelper CreateHelper()
{
return new SomeHelper();
}
public int Func(int x)
{
var helper = CreateHelper();
return helper.DoSomething(x);
}
}
internal class SomeHelper
{
public virtual int DoSomething(int x)
{
return -x;
}
}
Esto no se compilará porque no puede tener un método protegido que devuelva un tipo interno.
Su único recurso es no usar
SomeHelper
de esa manera, o hacer público
SomeHelper
.
(Podría hacer que
SomeHelper
una clase interna protegida de
Test
, pero eso no funcionará si
SomeHelper
está destinado a ser utilizado por otras clases que no se derivan de la clase base).
Con la introducción de la función
private protected
, puede declarar
CreateHelper()
manera:
private protected SomeHelper CreateHelper()
{
return new SomeHelper();
}
Ahora se compilará y no tendrá que exponer sus elementos internos.