Edytować. Właściwie, chociaż to, co powiem w mojej pierwszej odpowiedzi, jest ważne, to jest prawdziwy powód .:
Na początku było C. C nie jest zorientowane obiektowo (możesz przyjąć podejście obiektowe, ale to ci nie pomaga ani niczego nie wymusza).
Potem było C With Classes, które zostało później przemianowane na C ++. C ++ jest zorientowany obiektowo, dlatego zachęca do hermetyzacji i zapewnienia niezmienności obiektu - po skonstruowaniu oraz na początku i na końcu dowolnej metody obiekt jest w prawidłowym stanie.
Naturalną rzeczą jest wymuszenie, że klasa musi zawsze mieć konstruktora, aby upewnić się, że zaczyna się w poprawnym stanie - jeśli konstruktor nie musi nic robić, aby to zapewnić, pusty konstruktor udokumentuje ten fakt .
Ale celem z C ++ było być kompatybilnym z C do tego stopnia, że w miarę możliwości wszystkie prawidłowe programy w C były również prawidłowymi programami w C ++ (nie jest już tak aktywnym celem, a ewolucja C oddzielnie do C ++ oznacza, że już nie jest ).
Jednym z efektów tego było powielanie funkcjonalności między struct
a class
. Pierwszy robi rzeczy w C (domyślnie wszystko jest publiczne), a drugi robi wszystko w dobry sposób OO (domyślnie wszystko jest prywatne, deweloper aktywnie upublicznia to, czego chce).
Innym jest to, że aby C struct
, które nie mogło mieć konstruktora, ponieważ C nie ma konstruktorów, było poprawne w C ++, musi to mieć znaczenie w sposobie patrzenia na to w C ++. I tak, chociaż brak konstruktora byłby sprzeczny z praktyką OO polegającą na aktywnym zapewnianiu niezmiennika, C ++ przyjęło to jako oznaczenie, że istnieje domyślny konstruktor bez parametrów, który działał tak, jakby miał puste ciało.
Wszystkie C structs
były teraz poprawne w C ++ structs
(co oznaczało, że były takie same jak C ++ classes
ze wszystkim - składowymi i dziedziczeniem - publicznymi) traktowane z zewnątrz tak, jakby miały pojedynczy konstruktor bez parametrów.
Jeśli jednak umieściłeś konstruktor w a class
lub struct
, to robiłeś rzeczy w sposób C ++ / OO, a nie w C, i nie było potrzeby stosowania domyślnego konstruktora.
Ponieważ służył jako skrót, ludzie używali go nawet wtedy, gdy kompatybilność nie była możliwa w inny sposób (używał innych funkcji C ++ nie w C).
Dlatego kiedy pojawiła się Java (oparta na C ++ na wiele sposobów), a później C # (oparta na C ++ i Javie na różne sposoby), zachowali to podejście, ponieważ programiści mogli już być przyzwyczajeni.
Stroustrup pisze o tym w swoim The C ++ Programming Language, a nawet bardziej, skupiając się bardziej na tym, „dlaczego” języka w The Design and Evolution of C ++ .
=== Oryginalna odpowiedź ===
Powiedzmy, że tak się nie stało.
Powiedzmy, że nie chcę konstruktora bez parametrów, ponieważ bez niego nie mogę wprowadzić mojej klasy w znaczący stan. Rzeczywiście, jest to coś, co może się zdarzyć struct
w C # (ale jeśli nie możesz sensownie używać samych zer i zer struct
w C #, w najlepszym razie używasz niepublicznie widocznej optymalizacji, a poza tym masz wada projektowa w użyciu struct
).
Aby moja klasa mogła chronić swoje niezmienniki, potrzebuję specjalnego removeDefaultConstructor
słowa kluczowego. Musiałbym przynajmniej utworzyć prywatny konstruktor bez parametrów, aby upewnić się, że żaden kod wywołujący nie wywołuje wartości domyślnej.
Co jeszcze bardziej komplikuje język. Lepiej tego nie robić.
Podsumowując, najlepiej nie myśleć o dodawaniu konstruktora jako usuwaniu wartości domyślnej, lepiej pomyśleć o braku konstruktora jako cukru składniowego do dodawania konstruktora bez parametrów, który nic nie robi.