Qual è la differenza tra public, private, protected e having no access modifier?


Tutti i miei anni universitari ho usato public e vorrei conoscere la differenza tra public, private, e protected?

Inoltre cosa fa static invece di non avere nulla?

Author: Liam, 2009-03-05

14 answers

Modificatori di accesso

Pubblico

È possibile accedere al tipo o al membro da qualsiasi altro codice nello stesso assembly o in un altro assembly che lo faccia riferimento.

Privato

È possibile accedere al tipo o al membro solo tramite codice nella stessa classe o struttura.

Protetto

È possibile accedere al tipo o al membro solo tramite codice nella stessa classe o struttura classe derivata.

Privato protetto (aggiunto in C# 7.2)

È possibile accedere al tipo o al membro solo tramite codice nella stessa classe o struttura o in una classe derivata dallo stesso assembly, ma non da un altro assembly.

Interno

È possibile accedere al tipo o al membro da qualsiasi codice nello stesso assembly, ma non da un altro assembly.

Interno protetto

È possibile accedere al tipo o al membro da qualsiasi codice nello stesso assembly o da qualsiasi classe derivata in un altro assembly.

Quando non è impostato alcun modificatore di accesso, viene utilizzato un modificatore di accesso predefinito. Quindi c'è sempre una qualche forma di modificatore di accesso anche se non è impostato.

Statico

Il modificatore statico su una classe significa che la classe non può essere istanziata e che tutti i suoi membri sono statici. Un membro statico ha una versione indipendentemente dal numero di istanze del suo tipo di chiusura vengono create.

Una classe statica è fondamentalmente la stessa di una classe non statica, ma c'è una differenza: una classe statica non può essere istanziata esternamente. In altre parole, non è possibile utilizzare la nuova parola chiave per creare una variabile del tipo di classe. Poiché non esiste una variabile di istanza, è possibile accedere ai membri di una classe statica utilizzando il nome della classe stessa.

Tuttavia, esiste una cosa come statica costruttore . Qualsiasi classe può avere uno di questi, comprese le classi statiche. Non possono essere chiamati direttamente e non possono avere parametri (diversi da qualsiasi parametro di tipo sulla classe stessa). Un costruttore statico viene chiamato automaticamente per inizializzare la classe prima che venga creata la prima istanza o che venga fatto riferimento a qualsiasi membro statico. Assomiglia a questo:

static class Foo()
{
    static Foo()
    {
        Bar = "fubar";
    }

    public static string Bar { get; set; }
}

Le classi statiche sono spesso utilizzate come servizi, puoi usarle in questo modo:

MyStaticClass.ServiceMethod(...);
 895
Author: mbillard, 2018-09-04 08:36:38

Public - Se riesci a vedere la classe, allora puoi vedere il metodo

Private - Se sei parte di della classe, allora puoi vedere il metodo, altrimenti no.

Protetto - Come Privato, più tutti discendenti possono anche vedere il metodo.

Static (class) - Ricorda la distinzione tra "Class" e "Object" ? Lascia perdere tutto questo. Sono gli stessi con "static"... la classe è l'unica istanza di stesso.

Static (method) - Ogni volta che si utilizza questo metodo, avrà un frame di riferimento indipendente dall'istanza effettiva della classe di cui fa parte.

 144
Author: JosephStyons, 2009-03-05 17:22:22

Una panoramica grafica (sintesi in poche parole)

Visibilit

Per i valori predefiniti se non si mette alcun modificatore di accesso davanti, vedere qui:
Visibilità predefinita per classi e membri c# (campi, metodi, ecc.)?

Non nidificato

enum                              public
non-nested classes / structs      internal
interfaces                        internal
delegates in namespace            internal
class/struct member(s)            private
delegates nested in class/struct  private

Nidificato:

nested enum      public
nested interface public
nested class     private
nested struct    private
 131
Author: Stefan Steiger, 2017-05-23 10:31:39

Per quanto riguarda la domanda di Niente

  • I tipi di spazio dei nomi sono interni per impostazione predefinita
  • Qualsiasi membro del tipo, inclusi i tipi nidificati, è privato per impostazione predefinita
 22
Author: leppie, 2009-03-05 17:27:55

inserisci qui la descrizione dell'immagine

using System;

namespace ClassLibrary1
{
    public class SameAssemblyBaseClass
    {
        public string publicVariable = "public";
        protected string protectedVariable = "protected";
        protected internal string protected_InternalVariable = "protected internal";
        internal string internalVariable = "internal";
        private string privateVariable = "private";
        public void test()
        {
            // OK
            Console.WriteLine(privateVariable);

            // OK
            Console.WriteLine(publicVariable);

            // OK
            Console.WriteLine(protectedVariable);

            // OK
            Console.WriteLine(internalVariable);

            // OK
            Console.WriteLine(protected_InternalVariable);
        }
    }

    public class SameAssemblyDerivedClass : SameAssemblyBaseClass
    {
        public void test()
        {
            SameAssemblyDerivedClass p = new SameAssemblyDerivedClass();

            // NOT OK
            // Console.WriteLine(privateVariable);

            // OK
            Console.WriteLine(p.publicVariable);

            // OK
            Console.WriteLine(p.protectedVariable);

            // OK
            Console.WriteLine(p.internalVariable);

            // OK
            Console.WriteLine(p.protected_InternalVariable);
        }
    }

    public class SameAssemblyDifferentClass
    {
        public SameAssemblyDifferentClass()
        {
            SameAssemblyBaseClass p = new SameAssemblyBaseClass();

            // OK
            Console.WriteLine(p.publicVariable);

            // OK
            Console.WriteLine(p.internalVariable);

            // NOT OK
            // Console.WriteLine(privateVariable);

            // Error : 'ClassLibrary1.SameAssemblyBaseClass.protectedVariable' is inaccessible due to its protection level
            //Console.WriteLine(p.protectedVariable);

            // OK
            Console.WriteLine(p.protected_InternalVariable);
        }
    }
}

 using System;
        using ClassLibrary1;
        namespace ConsoleApplication4

{
    class DifferentAssemblyClass
    {
        public DifferentAssemblyClass()
        {
            SameAssemblyBaseClass p = new SameAssemblyBaseClass();

            // NOT OK
            // Console.WriteLine(p.privateVariable);

            // NOT OK
            // Console.WriteLine(p.internalVariable);

            // OK
            Console.WriteLine(p.publicVariable);

            // Error : 'ClassLibrary1.SameAssemblyBaseClass.protectedVariable' is inaccessible due to its protection level
            // Console.WriteLine(p.protectedVariable);

            // Error : 'ClassLibrary1.SameAssemblyBaseClass.protected_InternalVariable' is inaccessible due to its protection level
            // Console.WriteLine(p.protected_InternalVariable);
        }
    }

    class DifferentAssemblyDerivedClass : SameAssemblyBaseClass
    {
        static void Main(string[] args)
        {
            DifferentAssemblyDerivedClass p = new DifferentAssemblyDerivedClass();

            // NOT OK
            // Console.WriteLine(p.privateVariable);

            // NOT OK
            //Console.WriteLine(p.internalVariable);

            // OK
            Console.WriteLine(p.publicVariable);

            // OK
            Console.WriteLine(p.protectedVariable);

            // OK
            Console.WriteLine(p.protected_InternalVariable);

            SameAssemblyDerivedClass dd = new SameAssemblyDerivedClass();
            dd.test();
        }
    }
}
 17
Author: Narottam Goyal, 2015-05-24 07:24:49

Hmm.

Vedi qui: Modificatori di accesso .

In poche parole:

Public fornisce al metodo o al tipo una visibilità completa da altri tipi / classi.

Private consente solo al tipo contenente il metodo privato/variabile di accedere al metodo privato/variabile (si noti che le classi nidificate hanno anche accesso alle classi contenenti metodi/variabili private).

Protected è simile a private tranne che le classi derivate possono anche accedere a protected metodo.

"Niente" è VB.NET ' s equivalente a null. Anche se ti riferisci a "niente" che significa "nessun modificatore di accesso", allora dipende, anche se una regola empirica molto approssimativa (certamente in c#) è che se non si specifica esplicitamente un modificatore di accesso, la dichiarazione del metodo/variabile è di solito come restricted come può essere. cioè

public class MyClass
{
    string s = "";
}

È effettivamente lo stesso di:

public class MyClass
{
    private string s = "";
}

L'articolo MSDN collegato offrirà una descrizione completa quando non c'è accesso modificatore specificato esplicitamente.

 11
Author: CraigTP, 2016-01-24 22:41:39

Public - può essere accessibile da chiunque ovunque.
privato - è possibile accedere solo da with nella classe di cui fa parte.
protected - è possibile accedere solo da with nella classe o da qualsiasi oggetto che eredita dalla classe.

Niente è come null ma in VB.
Static significa che hai un'istanza di quell'oggetto, metodo per ogni istanza di quella classe.

 8
Author: Tony, 2015-09-17 13:20:46

Ripubblicando i diagrammi impressionanti da questa risposta.

Ecco tutti i modificatori di accesso nei diagrammi di Venn, da più limitanti a più promiscui:

private:
inserisci qui la descrizione dell'immagine

private protected: - aggiunto in C# 7.2
inserisci qui la descrizione dell'immagine

internal:
inserisci qui la descrizione dell'immagine

protected:
inserisci qui la descrizione dell'immagine

protected internal:
inserisci qui la descrizione dell'immagine

public:
inserisci qui la descrizione dell'immagine

 7
Author: Paul, 2018-07-03 08:25:40

Mmm...

Static significa che è possibile accedere a tale funzione senza avere un'istanza della classe.

È possibile accedere direttamente dalla definizione della classe.

 4
Author: gbianchi, 2009-03-05 13:53:14

Uno stato di Privato indica che le variabili possono essere accessibili solo da oggetti della stessa classe. Lo stato protetto estende tale accesso anche ai discendenti della classe.

"dalla tabella sopra possiamo vedere la deferenza tra privato e protetto... penso che entrambi siano uguali.... quindi qual è la necessità di quei due comandi separati "

Controllare MSDN collegamento per ulteriori informazioni

 4
Author: Grant Hood, 2012-01-07 17:57:32

Questi modificatori di accesso specificano dove sono visibili i tuoi membri. Probabilmente dovresti leggere questo. Prendi il link dato da IainMH come punto di partenza.

I membri statici sono uno per classe e non uno per istanza.

 3
Author: jpfollenius, 2009-03-05 13:52:47

Fai attenzione alla tua accessibilità delle tue classi. Le classi e i metodi pubblici e protetti sono di default accessibili a tutti.

Inoltre Microsoft non è molto esplicita nel mostrare i modificatori di accesso (pubblico, protetto, ecc.. parole chiave) quando vengono create nuove classi in Visual Studio. Quindi, fai attenzione e pensa alla tua accessibilità della tua classe perché è la porta per i tuoi interni di implementazione.

 3
Author: Patrick Peters, 2009-03-05 14:21:00

Penso che sia legato al buon design OOP. Se sei uno sviluppatore di una libreria, vuoi nascondere il funzionamento interno della tua libreria. In questo modo, è possibile modificare il funzionamento interno della libreria in seguito. Quindi metti i tuoi membri e i metodi di supporto come privati, e solo i metodi di interfaccia sono pubblici. I metodi che devono essere sovrascritti devono essere protetti.

 2
Author: Darius Kucinskas, 2013-08-28 19:53:25

C # ha in totale 6 modificatori di accesso:

Private: il membro dichiarato con questa accessibilità può essere visibile all'interno del tipo contenente, non è visibile a nessun tipo derivato, ad altri tipi nello stesso assembly o tipi al di fuori dell'assembly contenente. cioè, l'accesso è limitato al solo tipo contenente.

Protetto: il membro dichiarato con questa accessibilità può essere visibile all'interno dei tipi derivati dal tipo contenente all'interno del assieme contenente e i tipi derivati dal tipo contenente al di fuori dell'assieme contenente. cioè, l'accesso è limitato ai tipi derivati del tipo contenente.

Interno: il membro dichiarato con questa accessibilità può essere visibile all'interno dell'assembly contenente questo membro, non è visibile a nessun assembly al di fuori dell'assembly contenente. cioè, l'accesso è limitato a contenere solo assembly.

Interno protetto: Il membro dichiarato con questo l'accessibilità può essere visibile all'interno dei tipi derivati dal tipo contenente all'interno o all'esterno dell'assembly contenente, è visibile anche a qualsiasi tipo all'interno dell'assembly contenente. cioè, l'accesso è limitato a contenere tipi di assembly o derivati.

Public: il membro dichiarato con questa accessibilità può essere visibile all'interno dell'assembly contenente questo membro o qualsiasi altro assembly che fa riferimento all'assembly contenente. cioè, l'accesso non è limitato.

C # 7.2 è aggiunta di un nuovo livello di accessibilità:

Private protected : il membro dichiarato con questa accessibilità può essere visibile all'interno dei tipi derivati da questo tipo contenente all'interno dell'assembly contenente. Non è visibile a nessun tipo non derivato dal tipo contenente o all'esterno dell'assembly contenente. cioè, l'accesso è limitato ai tipi derivati all'interno dell'assembly contenente.

Fonte incluso un codice di esempio del nuovo accesso privato protetto modificatore

 1
Author: Baccata, 2017-12-20 09:27:01