Jakie są praktyczne zastosowania chronionego konstruktora?

Dlaczego ktoś deklaruje, że konstruktor jest chroniony? Wiem, że konstruktory są deklarowane jako prywatne w celu nie zezwalania na ich tworzenie na stosie.

Author: DavidRR, 2009-06-29

8 answers

Gdy klasa jest (zamierzona) klasą abstrakcyjną, chroniony konstruktor ma dokładnie rację. W tej sytuacji nie chcesz, aby obiekty były tworzone z instancji klasy, ale używaj ich tylko do dziedziczenia z.

Istnieją inne przypadki zastosowań, np. gdy określony zbiór parametrów konstrukcyjnych powinien być ograniczony do klas pochodnych.

 80
Author: Henk Holterman,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-29 12:30:15

One use could be factory patterns

 10
Author: Umair Ahmed,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-29 08:45:29

Konstruktory Niepubliczne są przydatne, gdy istnieją wymagania konstrukcyjne, których nie może zagwarantować wyłącznie konstruktor. Na przykład, jeśli metoda inicjalizacji musi być wywołana zaraz po konstruktorze lub jeśli obiekt musi zarejestrować się w jakimś obiekcie container / manager, musi to być wykonane poza konstruktorem. Ograniczając dostęp do konstruktora i podając tylko metodę fabryczną, możesz mieć pewność, że każda instancja otrzymana przez użytkownika spełni wszystkie jego Gwarancje. Jest to również powszechnie używane do implementacji Singletona, co jest tak naprawdę kolejną gwarancją, którą Klasa daje (że będzie tylko jedna instancja).

Powód uczynienia konstruktora chronionym, a nie prywatnym, jest taki sam jak w przypadku tworzenia jakiejkolwiek innej metody lub pola chronionego zamiast prywatnego: tak, że może być dziedziczone przez dzieci. Być może potrzebujesz publicznej, nie wirtualnej metody fabrycznej w klasie bazowej, która zwraca odwołania do wystąpień pochodnych klasy; klasy pochodne oczywiście chcą dostępu do konstruktorów nadrzędnych, ale nadal nie chcesz tworzyć ich poza fabryką.

 8
Author: Nick Lewis,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-29 22:31:11

Konstruktor chroniony oznacza, że tylko pochodne elementy mogą konstruować instancje klasy (i pochodne) używając tego konstruktora. Brzmi to trochę jak kurczak i jajko, ale czasami jest przydatne przy wdrażaniu klasowych fabryk.

 6
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-29 09:57:43

Chroniony konstruktor może być użyty do uczynienia klasy abstrakcyjną, gdy żadna z jej metod nie jest czysto wirtualna.

Nie jest to całkiem abstrakcyjne w sensie C++, ponieważ klasy przyjaciół nadal mogą go używać bez nadpisywania, ale wtedy trzeba by je zadeklarować.

 5
Author: Guidobot,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-06-27 13:29:33

Aby pozwolić podklasie używać konstruktora, który nie powinien być bezpośrednio Dostępny dla instancji.

 4
Author: Oliver Hanappi,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-29 08:48:49

Dla metod fabrycznych z efektami ubocznymi.

class mine {

  private:
    mine () {};

  protected:
    mine(int id) : m_id(id) {};

   int m_id;
   static int m_count;

  public:
    static mine* CreateOneOfMe() {
         return mine(m_count++);
    }

    int GetId() { return m_id; }

 };

To tworzy instancje klasy i gwarantuje, że każda z nich ma unikalny Przyrostowy identyfikator integer. Zauważ, że jeśli konstruktor, którego chcesz użyć, nie jest domyślny, musisz również ukryć domyślny.

 4
Author: sean riley,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-05-23 15:46:54

Możesz go użyć do ograniczenia klas, które mogą go utworzyć, na przykład:

class Level
{
private:

 Level();
 ¨Level();

 friend class LevelManager;
};

Jedyną klasą, która może utworzyć jej instancję jest klasa LevelManager, więc zawsze będziesz wiedział, że instancja Level jest utworzona w LevelManager.

 3
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-29 12:54:00