Wat is het verschil tussen openbaar, privé en beschermd?

Wanneer en waarom moet ik functies en variabelen public, privateen protectedgebruiken in een klasse? Wat is het verschil tussen beide?

Voorbeelden:

// Public
public $variable;
public function doSomething() {
  // ...
}
// Private
private $variable;
private function doSomething() {
  // ...
}
// Protected
protected $variable;
protected function doSomething() {
  // ...
}

Antwoord 1, autoriteit 100%

U gebruikt:

  • publicbereik om die eigenschap/methode overal, andere klassen en instanties van het object beschikbaar te maken.

  • privatebereik wanneer u wilt dat uw eigenschap/methode alleen zichtbaar is in zijn eigen klasse.

  • protectedbereik wanneer u uw eigenschap/methode zichtbaar wilt maken in alle klassen die de huidige klasse uitbreiden, inclusief de bovenliggende klasse.

Als je geen zichtbaarheidsmodifier gebruikt, is de eigenschap/methode openbaar.

Meer:(voor uitgebreide informatie)


Antwoord 2, autoriteit 92%

Openbaar:

Als u een methode (functie) of een eigenschap (variabele) declareert als public, zijn die methoden en eigenschappen toegankelijk via:

  • Dezelfde klas die het heeft aangegeven.
  • De klassen die de hierboven gedeclareerde klasse erven.
  • Alle vreemde elementen buiten deze klasse hebben ook toegang tot die dingen.

Voorbeeld:

<?php
class GrandPa
{
    public $name='Mark Henry';  // A public variable
}
class Daddy extends GrandPa // Inherited class
{
    function displayGrandPaName()
    {
        return $this->name; // The public variable will be available to the inherited class
    }
}
// Inherited class Daddy wants to know Grandpas Name
$daddy = new Daddy;
echo $daddy->displayGrandPaName(); // Prints 'Mark Henry'
// Public variables can also be accessed outside of the class!
$outsiderWantstoKnowGrandpasName = new GrandPa;
echo $outsiderWantstoKnowGrandpasName->name; // Prints 'Mark Henry'

Beschermd:

Wanneer u een methode (functie) of een eigenschap (variabele) als protecteddeclareert, zijn deze methoden en eigenschappen en eigenschappen toegankelijk via

  • dezelfde klasse die het heeft verklaard.
  • De klassen die de bovengenoemde verklaarde klasse erven.

Outsider-leden hebben geen toegang tot die variabelen. “Buitenstaanders” in de zin dat ze niet objects-instanties van de verklaarde klasse zelf zijn.

Voorbeeld:

<?php
class GrandPa
{
    protected $name = 'Mark Henry';
}
class Daddy extends GrandPa
{
    function displayGrandPaName()
    {
        return $this->name;
    }
}
$daddy = new Daddy;
echo $daddy->displayGrandPaName(); // Prints 'Mark Henry'
$outsiderWantstoKnowGrandpasName = new GrandPa;
echo $outsiderWantstoKnowGrandpasName->name; // Results in a Fatal Error

De exacte fout is dit:

PHP FATAL-fout: geen toegang tot beschermde eigenschap opa :: $ NAAM


Privé:

Wanneer u een methode (functie) of een eigenschap (variabele) declareert als private, zijn die methoden en eigenschappen toegankelijk via:

  • Dezelfde klas die het heeft aangegeven.

Externe leden hebben geen toegang tot deze variabelen. Buitenstaanders in de zin dat ze geen objectinstanties zijn van de gedeclareerde klasse zelfen zelfs niet de klassen die de gedeclareerde klasse erven.

Voorbeeld:

<?php
class GrandPa
{
    private $name = 'Mark Henry';
}
class Daddy extends GrandPa
{
    function displayGrandPaName()
    {
        return $this->name;
    }
}
$daddy = new Daddy;
echo $daddy->displayGrandPaName(); // Results in a Notice 
$outsiderWantstoKnowGrandpasName = new GrandPa;
echo $outsiderWantstoKnowGrandpasName->name; // Results in a Fatal Error

De exacte foutmeldingen zijn:

Opmerking: Ongedefinieerde eigenschap: Daddy::$name
Fatale fout: geen toegang tot privé-eigendom GrandPa::$name


De opa-klas ontleden met behulp van Reflectie

Dit onderwerp valt niet echt buiten het bestek, en ik voeg het hier toe om te bewijzen dat reflectie echt krachtig is. Zoals ik in de bovenstaande drie voorbeelden had aangegeven, zijn protecteden privateleden (eigenschappen en methoden) niet toegankelijk buiten de klas.

Met reflectie kun je echter het buitengewonedoen door zelfs toegang te krijgen tot protecteden privateleden buiten de klas!

Nou, wat is reflectie?

Reflection voegt de mogelijkheid toe om klassen, interfaces,
functies, methoden en extensies. Bovendien bieden ze manieren om
doc-opmerkingen ophalen voor functies, klassen en methoden.

Preambule

We hebben een klasse met de naam Grandpasen zeggen dat we drie eigenschappen hebben. Voor een gemakkelijk begrip, bedenk dat er drie opa’s zijn met namen:

  • Mark Henry
  • John Clash
  • Wil Jones

Laten we ze (wijzigen toewijzen) respectievelijk public, protecteden privatemaken. Je weet heel goed dat protecteden privateleden niet toegankelijk zijn buiten de klas. Laten we nu de bewering tegenspreken met behulp van reflectie.

De code

<?php
class GrandPas   // The Grandfather's class
{
    public     $name1 = 'Mark Henry';  // This grandpa is mapped to a public modifier
    protected  $name2 = 'John Clash';  // This grandpa is mapped to a protected  modifier
    private    $name3 = 'Will Jones';  // This grandpa is mapped to a private modifier
}
# Scenario 1: without reflection
$granpaWithoutReflection = new GrandPas;
# Normal looping to print all the members of this class
echo "#Scenario 1: Without reflection<br>";
echo "Printing members the usual way.. (without reflection)<br>";
foreach($granpaWithoutReflection as $k=>$v)
{
    echo "The name of grandpa is $v and he resides in the variable $k<br>";
}
echo "<br>";
#Scenario 2: Using reflection
$granpa = new ReflectionClass('GrandPas'); // Pass the Grandpas class as the input for the Reflection class
$granpaNames=$granpa->getDefaultProperties(); // Gets all the properties of the Grandpas class (Even though it is a protected or private)
echo "#Scenario 2: With reflection<br>";
echo "Printing members the 'reflect' way..<br>";
foreach($granpaNames as $k=>$v)
{
    echo "The name of grandpa is $v and he resides in the variable $k<br>";
}

Uitvoer:

#Scenario 1: Without reflection
Printing members the usual way.. (Without reflection)
The name of grandpa is Mark Henry and he resides in the variable name1
#Scenario 2: With reflection
Printing members the 'reflect' way..
The name of grandpa is Mark Henry and he resides in the variable name1
The name of grandpa is John Clash and he resides in the variable name2
The name of grandpa is Will Jones and he resides in the variable name3

Veelvoorkomende misvattingen:

Verwar het onderstaande voorbeeld niet. Zoals je nog steeds kunt zien, zijn de privateen protectedleden niet toegankelijk buitenvan de klas zonder reflectie

<?php
class GrandPas   // The Grandfather's class
{
    public     $name1 = 'Mark Henry';  // This grandpa is mapped to a public modifier
    protected  $name2 = 'John Clash';  // This grandpa is mapped to a protected modifier
    private    $name3 = 'Will Jones';  // This grandpa is mapped to a private modifier
}
$granpaWithoutReflections = new GrandPas;
print_r($granpaWithoutReflections);

Uitvoer:

GrandPas Object
(
    [name1] => Mark Henry
    [name2:protected] => John Clash
    [name3:GrandPas:private] => Will Jones
)

Foutopsporingsfuncties

print_r, var_exporten var_dumpzijn foutopsporingsfuncties. Ze presenteren informatie over een variabele in een voor mensen leesbare vorm. Deze drie functies onthullen de protecteden privateeigenschappen van objecten met PHP 5. Statische klasseleden zullen nietworden getoond.


Meer bronnen:



Antwoord 3, autoriteit 6%

Het wordt doorgaans als een goede gewoonte beschouwd om standaard de laagste zichtbaarheid te gebruiken die vereist is, omdat dit de inkapseling van gegevens en een goed interface-ontwerp bevordert. Denk bij het overwegen van lidvariabele en methodezichtbaarheid na over de rol die het lid speelt in de interactie met andere objecten.

Als u “codeert naar een interface in plaats van implementatie”, dan is het meestal vrij eenvoudig om zichtbaarheidsbeslissingen te nemen. Over het algemeen moeten variabelen privé of beschermd zijn, tenzij u een goede reden hebt om ze openbaar te maken. Gebruik in plaats daarvan openbare accessors (getters/setters) om de toegang tot de interne onderdelen van een klas te beperken en te reguleren.

Om een auto als analogie te gebruiken, zouden zaken als snelheid, versnelling en richting privé-instantievariabelen zijn. U wilt niet dat de bestuurder zaken als de lucht/brandstofverhouding direct manipuleert. In plaats daarvan stelt u een beperkt aantal acties bloot als openbare methoden. De interface naar een auto kan methoden bevatten zoals accelerate(), deccelerate()/brake(), setGear(), turnLeft(), turnRight(), enz.

De bestuurder weet niet hoe deze acties worden uitgevoerd door de binnenkant van de auto en het kan hem ook niet schelen hoe deze acties worden uitgevoerd, en het blootstellen van die functionaliteit kan gevaarlijk zijn voor de bestuurder en anderen op de weg. Vandaar de goede gewoonte om een openbare interface te ontwerpen en de gegevens achter die interface in te kapselen.

Met deze aanpak kun je ook de implementatie van de openbare methoden in je klas wijzigen en verbeteren zonder het contract van de interface met de clientcode te verbreken. U kunt bijvoorbeeld de methode accelerate()verbeteren om zuiniger met brandstof om te gaan, maar het gebruik van die methode blijft hetzelfde; klantcode hoeft niet te worden gewijzigd, maar plukt toch de vruchten van uw efficiëntieverbetering.

Bewerken:aangezien het lijkt alsof je nog steeds bezig bent met het leren van objectgeoriënteerde concepten (die veel moeilijker te beheersen zijn dan de syntaxis van welke taal dan ook), raad ik je ten zeersteaan het ophalen van een kopie van PHP Objects, Patterns, and Practicedoor Matt Zandstra. Dit is het boek dat me voor het eerst leerde hoeOOP effectief te gebruiken, in plaats van me alleen de syntaxis te leren. Ik had de syntaxis jaren van tevoren geleerd, maar dat was nutteloos zonder het ‘waarom’ van OOP te begrijpen.


Antwoord 4, autoriteit 6%

private– alleen toegankelijk vanuit BINNEN de klas

protected– is toegankelijk vanuit de klassen en ervende klassen

public– is ook toegankelijk via de code buiten de klas

Dit geldt voor zowel functies als variabelen.


Antwoord 5, Autoriteit 2%

Het verschil is als volgt:

public:: Een openbare variabele of methode is direct toegankelijk via elke gebruiker van de klasse.

protected:: Een beschermde variabele of methode kan niet worden geopend door gebruikers van de klasse, maar is toegankelijk binnen een subklasse die van de klasse erft.

private:: Een particuliere variabele of methode kan alleen intern worden toegankelijk vanuit de klas waarin deze is gedefinieerd. Dit betekent dat een privévariabele of methode niet kan worden genoemd van een kind dat de klasse uitbreidt.


Antwoord 6

zichtbaarheid scopes met abstracte voorbeelden :: maakt eenvoudig te begrijpen

Deze zichtbaarheid van een eigenschap of methode wordt gedefinieerd door de vooraf bevestigende verklaring van een van de drie zoekwoord (openbaar, beschermd en privé)

Public : Als een eigenschap of methode is gedefinieerd als openbaar, betekent dit dat het zowel toegang als gemanipuleerd kan zijn door iets dat naar object kan verwijzen.

  • abstract, bijvoorbeeld. Denk aan openbare zichtbaarheidsbereik als “openbare picknick” waaraan iemand kan komen.

Beschermd: Wanneer een eigenschap of methode zichtbaarheid is ingesteld op beschermde leden kunnen alleen toegang krijgen binnen de klasse zelf en door erfdeel en versterker; ervende klassen. (Geërfd: – een klasse kan alle eigenschappen en methoden van een andere klasse hebben).

  • Denk aan een beschermd zichtbereik als ‘Bedrijfspicknick’waar bedrijfsleden en hun familieleden zijn toegestaan, niet het publiek. Dit is de meest voorkomende beperking van het bereik.

Privé:wanneer de zichtbaarheid van een eigenschap of methode is ingesteld op privé, heeft alleen de klasse met de privéleden toegang tot die methoden en eigenschappen (intern binnen de klasse), ongeacht de klassenrelatie daar misschien.

  • denk met picknickanalogie als een “bedrijfspicknick waar alleen de bedrijfsleden zijn toegestaan”tijdens de picknick. geen familie noch algemeen publiek zijn toegestaan.

Antwoord 7

/**
 * Define MyClass
 */
class MyClass
{
    public $public = 'Public';
    protected $protected = 'Protected';
    private $private = 'Private';
    function printHello()
    {
        echo $this->public;
        echo $this->protected;
        echo $this->private;
    }
}
$obj = new MyClass();
echo $obj->public; // Works
echo $obj->protected; // Fatal Error
echo $obj->private; // Fatal Error
$obj->printHello(); // Shows Public, Protected and Private
/**
 * Define MyClass2
 */
class MyClass2 extends MyClass
{
    // We can redeclare the public and protected method, but not private
    protected $protected = 'Protected2';
    function printHello()
    {
        echo $this->public;
        echo $this->protected;
        echo $this->private;
    }
}
$obj2 = new MyClass2();
echo $obj2->public; // Works
echo $obj2->private; // Undefined
echo $obj2->protected; // Fatal Error
$obj2->printHello(); // Shows Public, Protected2, Undefined

Geëxtraheerd uit :

http://php.net/manual/en/language.oop5.visibility.php


Antwoord 8

⚡️ Hier is een gemakkelijke manier om het bereik van public, protecteden privatete onthouden.

public:

    Bereik

  • public: een openbare variabele/functie is beschikbaar voor zowel objecten als andere klassen.

protected:

  • protectedbereik: een beveiligde variabele/functie is beschikbaar voor alle klassen die de huidige klasse uitbreiden.
  • Nee! Objecten hebben geen toegang tot dit bereik

private:

  • privatescope: een private variabele/functie is alleen zichtbaar in de huidige klasse waarin deze wordt gedefinieerd.
  • Nee! Klasse die de huidige klasse uitbreidt, heeft geen toegang tot dit bereik.
  • Nee! Objecten hebben geen toegang tot dit bereik.

Lees de Zichtbaarheidvan een methode of variabele in de PHP-handleiding.


Antwoord 9

Overwegend ‘wanneer‘:
Ik heb de neiging om in eerste instantie alles als privé aan te geven, als ik het niet precies zeker weet. De reden hiervoor is dat het meestal veel gemakkelijker is om een privémethode openbaar te maken dan andersom. Dat komt omdat je er in ieder geval zeker van kunt zijn dat de private methode nergens anders is gebruikt dan in de klasse zelf. Een openbare methode kan al overal in gebruik zijn, die mogelijk een uitgebreide herschrijving vereist.

Update: ik ga tegenwoordig voor een standaard van protected, omdat ik ben gaan ontdekken dat het goed genoeg is voor inkapseling en niet in de weg staat wanneer Ik verleng lessen (die ik toch probeer te vermijden). Alleen als ik een goede reden heb om de andere twee te gebruiken, doe ik dat.

Een goede reden voor een private-methode zou er een zijn die iets inherent aan dat object implementeert dat zelfs een uitbreidende klasse niet zou moeten veranderen (feitelijke reden, naast inkapseling, zoals intern staatsbeheer). Uiteindelijk is het nog steeds gemakkelijk genoeg om op te sporen waar een protectedmethode gewoonlijk wordt gebruikt, dus ik gebruik tegenwoordig standaard protected. Misschien geen 100% objectieve “in de loopgraven” ervaring, dat geef ik toe.


Antwoord 10

Voor mij is dit de handigstemanier om de drie eigenschapstypen te begrijpen:

Openbaar: gebruik dit als je het goed vindt dat deze variabele direct toegankelijk is en kan worden gewijzigd vanaf elke plek in je code.

Voorbeeld van gebruik van buiten de klas:

$myObject = new MyObject()
$myObject->publicVar = 'newvalue';
$pubVar = $myObject->publicVar;

Beveiligd: gebruik dit als je andere programmeurs (en jezelf) wilt dwingen om getters/setters buiten de klas te gebruiken bij het openen en instellen van variabelen (maar je moet consistent zijn en de getters en setters in de klas). Dit of privateis meestal de standaard manier waarop u alle klasse-eigenschappen moet instellen.

Waarom? Want als je op een bepaald moment in de toekomst (misschien zelfs binnen 5 minuten) besluit dat je de waarde die voor die eigenschap wordt geretourneerd, wilt manipuleren of er iets mee wilt doen voordat je het krijgt/instelt, dan kun je dat doen zonder overal waar je hebt te refactoren heb het in je project gebruikt.

Voorbeeld van gebruik van buiten de klas:

$myObject = new MyObject()
$myObject->setProtectedVar('newvalue');
$protectedVar = $myObject->getProtectedVar();

Privé: privateeigenschappen lijken erg op protectedeigenschappen. Maar het onderscheidende kenmerk/verschil is dat het privatemaken het ook ontoegankelijk maakt voor onderliggende klassen zonder gebruik te maken van de getter of setter van de bovenliggende klasse.

Dus in principe, als je getters en setters gebruikt voor een eigenschap (of als het alleen intern wordt gebruikt door de bovenliggende klasse en het niet bedoeld is om ergens anders toegankelijk te zijn), kun je het net zo goed private, om te voorkomen dat iemand het rechtstreeks probeert te gebruiken en bugs introduceert.

Voorbeeld van gebruik binnen een onderliggende klasse (die MyObject uitbreidt):

$this->setPrivateVar('newvalue');
$privateVar = $this->getPrivateVar();

Antwoord 11

De PHP-handleiding heeft de vraag hiergoed gelezen.

De zichtbaarheid van een eigenschap of methode kan worden gedefinieerd door de declaratie vooraf te laten gaan met de trefwoorden public, protected of private. Klasleden die openbaar zijn verklaard, zijn overal toegankelijk. Leden die beschermd zijn verklaard, zijn alleen toegankelijk binnen de klasse zelf en door geërfde en bovenliggende klassen. Leden die als privé zijn gedeclareerd, zijn alleen toegankelijk voor de klasse die het lid definieert.


Antwoord 12

Een oude vraag nieuw leven inblazen, maar ik denk dat een heel goede manier om hierover na te denken is in termen van de API die u definieert.

  • public– Alles dat als openbaar is gemarkeerd, maakt deel uit van de API die iedereen die uw klasse/interface/andere gebruikt, zal gebruiken en waarop iedereen kan vertrouwen.

  • protected– Laat je niet misleiden, dit is ook onderdeel van de API! Mensen kunnen subclasseren, je code uitbreiden en alles gebruiken dat als beschermd is gemarkeerd.

  • private– Privé-eigenschappen en -methoden kunnen zo vaak worden gewijzigd als u wilt. Niemand anders kan deze gebruiken. Dit zijn de enige dingen die u kunt veranderen zonder ingrijpende wijzigingen aan te brengen.

Of in Semver-termen:

  • Wijzigingen aan alles wat publicof protectedis, moeten als BELANGRIJKE wijzigingen worden beschouwd.

  • Alles wat nieuw is publicof protectedmoet (minstens) KLEINIG zijn

  • Alleen nieuwe/wijzigingen aan iets privatekunnen PATCH

  • zijn

Dus als het gaat om het onderhouden van code, is het goed om voorzichtig te zijn met wat je publicof protectedmaakt, omdat dit de dingen zijn die je je gebruikers belooft.


Antwoord 13

Ze zijn er voor verschillende niveaus van inkapseling


Antwoord 14

Variabelen in PHP worden in drie verschillende typen gegoten:

Openbaar: waarden van deze variabele typen zijn beschikbaar in alle scopes en vragen om uitvoering van uw code.
declareren als: public $examTimeTable;

Privé: waarden van dit type variabele zijn alleen beschikbaar voor de klasse waartoe het behoort.
private $classRoomComputers;

Beveiligd: waarden van deze klasse alleen en alleen beschikbaar wanneer toegang is verleend in een vorm van overerving of hun onderliggende klasse. algemeen gebruikt ::om toegang te verlenen aan ouderklasse

protected $familyWealth;


Antwoord 15

Als we objectgeoriënteerde php in ons project volgen, moeten we enkele regels volgen om toegangsmodifiers in php te gebruiken. Vandaag gaan we duidelijk leren wat toegangsmodificator is en hoe we deze kunnen gebruiken. PHP-toegangsmodifiers worden gebruikt om toegangsrechten in te stellen voor PHP-klassen en hun leden, de functies en variabelen die zijn gedefinieerd binnen het klassenbereik. In php zijn er drie scopes voor klasleden.

  1. OPENBAAR
  2. PRIVÉ
  3. BESCHERMD

Laten we nu de volgende afbeelding eens bekijken om het toegangsniveau van de toegangsmodifier te begrijpen

Laten we nu eens kijken naar de volgende lijst om meer te weten te komen over de mogelijke PHP-sleutelwoorden die worden gebruikt als toegangsmodifiers.

public :- class of zijn leden gedefinieerd met deze toegangsmodifier zullen overal toegankelijk zijn, zelfs buiten het bereik van de class.

private :- leden van de klas met dit trefwoord hebben toegang binnen de klas zelf. we hebben geen toegang tot privégegevens van de subklasse. Het beschermt leden tegen toegang van buitenaf.

Beschermd: – hetzelfde als privé, behalve door subclasses toe te staan ​​om toegang te krijgen tot beschermde superclass-leden.

Zie nu de tabel om toegang te begrijpen Modifier Lees volledig artikel PHP Access Modifire


Antwoord 16

Public: is een standaardstatus wanneer u een variabele of methode declareert, toegankelijk is via iets rechtstreeks naar het object.

protected: Alleen toegankelijk zijn binnen het object en de subclasses.

Private: kan alleen worden verwezen in het object, geen subklassen.


Antwoord 17

De vermelde trefwoorden zijn toegangsmodificatoren en helpen ons inkapseling (of informatie verstopt) te implementeren. Ze vertellen de compiler die andere klassen toegang moeten hebben tot het veld of de methode die wordt gedefinieerd.

Privé – Alleen de huidige klasse heeft toegang tot het veld of de methode.

Beschermd – Alleen de huidige klasse en subclasses (en soms ook dezelfde klassen van dezelfde pakketten) van deze klasse hebben toegang tot het veld of de methode.

Public – Elke klasse kan verwijzen naar het veld of de methode bellen.

Other episodes