Can we live without constructors?

Let’s say in some reason all objects are created this way $obj = CLASS::getInstance(). Then we inject dependencies using setters and perform starting initialization using $obj->initInstance(); Are there any real troubles or situations, which can’t be solved, if we won’t use constructors at all?

P.s. the reason to create object this way, is that we can replace class inside getInstance() according to some rules.

I’m working in PHP, if that matter

8

I’d say that this severly hinders your design space.

Constructors are a great place to initialize and validate parameters passed in. If you can no longer use them for that, then initialization, state handling (or plain out denying constructor of “broken” objects) becomes a lot harder and partially impossible.

For example, if every Foo object needs a Frobnicator then it might check in its constructor if the Frobnicator is non-null. If you take away the constructor, then it gets harder to check. Do you check at every point where it would be used? In an init() method (effectively externalizing the constructor method)? Never check it and hope for the best?

While you could probably still implement everything (after all, you’re still turing complete), some things will be a lot harder to do.

Personally I’d suggest looking into Dependency Injection/Inversion of Control. These techniques also allow switching concrete implementation classes, but they don’t prevent writing/using constructors.

3

2 advantages to constructors:

Constructors allow for the an object’s construction steps to be done atomically.

I could avoid a constructor and use setters for everything, but what about mandatory properties as Joachim Sauer suggested? With a constructor, an object owns its own construction logic so as to ensure that there are no invalid instances of such class.

If creating an instance of Foo requires 3 properties to be set, the constructor could take a reference to all 3, validate them and throw an exception if they are invalid.

Encapsulation

By relying solely on setters, the burden is on the consumer of an object to build it properly. There could be different combinations of properties that are valid.

For example, every Foo instance needs either an instance of Bar as property bar or an instance of BarFinder as property barFinder. It can use either one. You can create a constructor for every valid set of parameters and enforce the conventions that way.

The logic and semantics for the objects live within the object itself. It’s good encapsulation.

Yes, you can live without constructors.

Sure, you may end up with a lot of duplicated boiler plate code. And if your application is of any scale, you’ll likely spend a lot of time trying to locate the source of a problem when that boilerplate code isnt used consistently across the application.

But no, you don’t strictly ‘need’ your own constructors. Of course, you don’t strictly ‘need’ classes and objects, either.

Now if your goal is to use some sort of factory pattern for object creation, that isnt mutually exclusive to using constructors when initializing your objects.

2

The advantage of using constructors is that they make it easier to ensure that you will never have an invalid object.

A constructor gives you the opportunity to set all member variables of the object to a valid state. When you then ensure that no mutator method can change the object to an invalid state, you will never have an invalid object, which will save you from a lot of bugs.

But when a new object is created in an invalid state and you must call some setters to put it into a valid state in which it can be used, you are risking that a consumer of the class forgets to call these setters or calls them incorrectly and you end up with an invalid object.

A workaround could be to create objects only through a factory-method which checks every object it creates for validity before returning it to the caller.

$obj = CLASS::getInstance(). Then we inject dependencies using setters and perform starting initialization using $obj->initInstance();

I think you’re making this more difficult than it needs to be. We can inject dependencies just fine through the constructor – and if you have a lot of them, just use a dictionary-like structure so you can specify what ones you want to use:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>$obj = new CLASS(array(
'Frobnicator' => (),
'Foonicator' => (),
));
</code>
<code>$obj = new CLASS(array( 'Frobnicator' => (), 'Foonicator' => (), )); </code>
$obj = new CLASS(array(
    'Frobnicator' => (),
    'Foonicator' => (),
));

And within the constructor, you can ensure consistency like so:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>if (!array_key_exists('Frobnicator', $args)) {
throw new Exception('Frobnicator required');
}
if (!array_key_exists('Foonicator', $args)) {
$args['Foonicator'] = new DefaultFoonicator();
}
</code>
<code>if (!array_key_exists('Frobnicator', $args)) { throw new Exception('Frobnicator required'); } if (!array_key_exists('Foonicator', $args)) { $args['Foonicator'] = new DefaultFoonicator(); } </code>
if (!array_key_exists('Frobnicator', $args)) {
    throw new Exception('Frobnicator required');
}
if (!array_key_exists('Foonicator', $args)) {
    $args['Foonicator'] = new DefaultFoonicator();
}

$args can then be used to set private members as necessary.

When done entirely within the constructor like so, there will never be an intermediate state where $obj exists but is not initialized, as there would be in the system described in the question. It’s better to avoid such intermediate states, because you can’t guarantee the object is always going to be used correctly.

I was actually thinking about similar things.

The question I asked was “What constructor does, and is it possible to do it differently?” I reached those conclusions:

  • It ensures some properties are initialized. By accepting them as parameters and setting them. But this could easily be enforced by compiler. By simply annotating the fields or properties as “required” the compiler would check during creation of the instance if everything is properly set. The call to create the instance would probably be same, there just wouldn’t be any constructor method.

  • Ensures the properties are valid. This could be easily achieved by assert condition. Again you would just annotate the properties with correct conditions. Some languages already do this.

  • Some more complex construction logic. Modern patterns don’t recommend to do that in constructor, but propose using specialized factory methods or classes. So the use of constructors in this case is minimal.

So to answer your question: Yes, I believe it is possible. But it would require some big changes in language design.

And I just noticed my answer is pretty OT.

Yes, you can do nearly everything without using constructors but this is clearly squandering benefits of Object-Oriented Programming languages.

In modern languages (I’ll talk here about C# which I program in) you can limit parts of code that can be run only in a constructor. Thanks to which you can avoid clumsy mistakes. One of such a thing is readonly modifier:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>public class A {
readonly string rostring;
public A(string arg) {
rostring = arg;
}
public static A CreateInstance(string arg) {
var result = new A();
A.rostring = arg; // < because of this the code won't compile!
return result;
}
}
</code>
<code>public class A { readonly string rostring; public A(string arg) { rostring = arg; } public static A CreateInstance(string arg) { var result = new A(); A.rostring = arg; // < because of this the code won't compile! return result; } } </code>
public class A {
    readonly string rostring;

    public A(string arg) {
        rostring = arg;
    }

    public static A CreateInstance(string arg) {
        var result = new A();
        A.rostring = arg;  // < because of this the code won't compile!
        return result;
    }
}

As recommended by Joachim Sauer previously instead of using Factory design patter read about Dependency Injection. I would recommend reading Dependency Injection in .NET by Mark Seemann.

Instantiate an object with a type depending on the requirements it is absolutely possible. It could be the object itself, using global variables of the system to return a specific type.

However, have a class in the code that can be “All” is the concept of dynamic type. I personally believe this approach create inconsistency in your code, make the test complexes*, and “the future becomes uncertain” with respect to the flow of the proposed work.

*I am referring to the fact that the tests must consider first the type, second the result you want to achieve. Then you are creating large nested test.

To balance some of the other answers, claiming:

A constructor gives you the opportunity to set all member variables of
the object to a valid state… you will never have an invalid object, which will save you from a lot of bugs.

and

With a constructor, an object owns its own construction logic so as to ensure that there are no invalid instances of such class.

Such statements sometimes imply the assumption that:

If an class has a constructor that, by the time it exits, has put the object into a valid state, and none of the class’s methods mutate that state to make it invalid, then it is impossible for code outside the class to detect an object of that class in an invalid state.

But this is not quite true. Most languages do not have a rule against a constructor passing this (or self or whatever the language calls it) to external code. Such a constructor completely abides by the rule stated above, and yet it risks exposing semi-constructed objects to external code. It’s a minor point but easily overlooked.

This is somewhat anecdotal, but I usually reserve constructors for state essential for the object to be complete and usable. Barring any setter-injection, once the constructor is run, my object should be able to perform the tasks required of it.

Anything that can be deferred, I leave out of the constructor (preparing output values, etc). With this approach, I feel not using constructors for anything but dependency injection makes sense.

This also has the added benefit of hard-wiring your mental design process to not do anything prematurely. You won’t initialize or perform logic that may never end up being used because at best all you’re doing is basic setup for the work ahead.

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa

Can we live without constructors?

Let’s say in some reason all objects are created this way $obj = CLASS::getInstance(). Then we inject dependencies using setters and perform starting initialization using $obj->initInstance(); Are there any real troubles or situations, which can’t be solved, if we won’t use constructors at all?

P.s. the reason to create object this way, is that we can replace class inside getInstance() according to some rules.

I’m working in PHP, if that matter

8

I’d say that this severly hinders your design space.

Constructors are a great place to initialize and validate parameters passed in. If you can no longer use them for that, then initialization, state handling (or plain out denying constructor of “broken” objects) becomes a lot harder and partially impossible.

For example, if every Foo object needs a Frobnicator then it might check in its constructor if the Frobnicator is non-null. If you take away the constructor, then it gets harder to check. Do you check at every point where it would be used? In an init() method (effectively externalizing the constructor method)? Never check it and hope for the best?

While you could probably still implement everything (after all, you’re still turing complete), some things will be a lot harder to do.

Personally I’d suggest looking into Dependency Injection/Inversion of Control. These techniques also allow switching concrete implementation classes, but they don’t prevent writing/using constructors.

3

2 advantages to constructors:

Constructors allow for the an object’s construction steps to be done atomically.

I could avoid a constructor and use setters for everything, but what about mandatory properties as Joachim Sauer suggested? With a constructor, an object owns its own construction logic so as to ensure that there are no invalid instances of such class.

If creating an instance of Foo requires 3 properties to be set, the constructor could take a reference to all 3, validate them and throw an exception if they are invalid.

Encapsulation

By relying solely on setters, the burden is on the consumer of an object to build it properly. There could be different combinations of properties that are valid.

For example, every Foo instance needs either an instance of Bar as property bar or an instance of BarFinder as property barFinder. It can use either one. You can create a constructor for every valid set of parameters and enforce the conventions that way.

The logic and semantics for the objects live within the object itself. It’s good encapsulation.

Yes, you can live without constructors.

Sure, you may end up with a lot of duplicated boiler plate code. And if your application is of any scale, you’ll likely spend a lot of time trying to locate the source of a problem when that boilerplate code isnt used consistently across the application.

But no, you don’t strictly ‘need’ your own constructors. Of course, you don’t strictly ‘need’ classes and objects, either.

Now if your goal is to use some sort of factory pattern for object creation, that isnt mutually exclusive to using constructors when initializing your objects.

2

The advantage of using constructors is that they make it easier to ensure that you will never have an invalid object.

A constructor gives you the opportunity to set all member variables of the object to a valid state. When you then ensure that no mutator method can change the object to an invalid state, you will never have an invalid object, which will save you from a lot of bugs.

But when a new object is created in an invalid state and you must call some setters to put it into a valid state in which it can be used, you are risking that a consumer of the class forgets to call these setters or calls them incorrectly and you end up with an invalid object.

A workaround could be to create objects only through a factory-method which checks every object it creates for validity before returning it to the caller.

$obj = CLASS::getInstance(). Then we inject dependencies using setters and perform starting initialization using $obj->initInstance();

I think you’re making this more difficult than it needs to be. We can inject dependencies just fine through the constructor – and if you have a lot of them, just use a dictionary-like structure so you can specify what ones you want to use:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>$obj = new CLASS(array(
'Frobnicator' => (),
'Foonicator' => (),
));
</code>
<code>$obj = new CLASS(array( 'Frobnicator' => (), 'Foonicator' => (), )); </code>
$obj = new CLASS(array(
    'Frobnicator' => (),
    'Foonicator' => (),
));

And within the constructor, you can ensure consistency like so:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>if (!array_key_exists('Frobnicator', $args)) {
throw new Exception('Frobnicator required');
}
if (!array_key_exists('Foonicator', $args)) {
$args['Foonicator'] = new DefaultFoonicator();
}
</code>
<code>if (!array_key_exists('Frobnicator', $args)) { throw new Exception('Frobnicator required'); } if (!array_key_exists('Foonicator', $args)) { $args['Foonicator'] = new DefaultFoonicator(); } </code>
if (!array_key_exists('Frobnicator', $args)) {
    throw new Exception('Frobnicator required');
}
if (!array_key_exists('Foonicator', $args)) {
    $args['Foonicator'] = new DefaultFoonicator();
}

$args can then be used to set private members as necessary.

When done entirely within the constructor like so, there will never be an intermediate state where $obj exists but is not initialized, as there would be in the system described in the question. It’s better to avoid such intermediate states, because you can’t guarantee the object is always going to be used correctly.

I was actually thinking about similar things.

The question I asked was “What constructor does, and is it possible to do it differently?” I reached those conclusions:

  • It ensures some properties are initialized. By accepting them as parameters and setting them. But this could easily be enforced by compiler. By simply annotating the fields or properties as “required” the compiler would check during creation of the instance if everything is properly set. The call to create the instance would probably be same, there just wouldn’t be any constructor method.

  • Ensures the properties are valid. This could be easily achieved by assert condition. Again you would just annotate the properties with correct conditions. Some languages already do this.

  • Some more complex construction logic. Modern patterns don’t recommend to do that in constructor, but propose using specialized factory methods or classes. So the use of constructors in this case is minimal.

So to answer your question: Yes, I believe it is possible. But it would require some big changes in language design.

And I just noticed my answer is pretty OT.

Yes, you can do nearly everything without using constructors but this is clearly squandering benefits of Object-Oriented Programming languages.

In modern languages (I’ll talk here about C# which I program in) you can limit parts of code that can be run only in a constructor. Thanks to which you can avoid clumsy mistakes. One of such a thing is readonly modifier:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>public class A {
readonly string rostring;
public A(string arg) {
rostring = arg;
}
public static A CreateInstance(string arg) {
var result = new A();
A.rostring = arg; // < because of this the code won't compile!
return result;
}
}
</code>
<code>public class A { readonly string rostring; public A(string arg) { rostring = arg; } public static A CreateInstance(string arg) { var result = new A(); A.rostring = arg; // < because of this the code won't compile! return result; } } </code>
public class A {
    readonly string rostring;

    public A(string arg) {
        rostring = arg;
    }

    public static A CreateInstance(string arg) {
        var result = new A();
        A.rostring = arg;  // < because of this the code won't compile!
        return result;
    }
}

As recommended by Joachim Sauer previously instead of using Factory design patter read about Dependency Injection. I would recommend reading Dependency Injection in .NET by Mark Seemann.

Instantiate an object with a type depending on the requirements it is absolutely possible. It could be the object itself, using global variables of the system to return a specific type.

However, have a class in the code that can be “All” is the concept of dynamic type. I personally believe this approach create inconsistency in your code, make the test complexes*, and “the future becomes uncertain” with respect to the flow of the proposed work.

*I am referring to the fact that the tests must consider first the type, second the result you want to achieve. Then you are creating large nested test.

To balance some of the other answers, claiming:

A constructor gives you the opportunity to set all member variables of
the object to a valid state… you will never have an invalid object, which will save you from a lot of bugs.

and

With a constructor, an object owns its own construction logic so as to ensure that there are no invalid instances of such class.

Such statements sometimes imply the assumption that:

If an class has a constructor that, by the time it exits, has put the object into a valid state, and none of the class’s methods mutate that state to make it invalid, then it is impossible for code outside the class to detect an object of that class in an invalid state.

But this is not quite true. Most languages do not have a rule against a constructor passing this (or self or whatever the language calls it) to external code. Such a constructor completely abides by the rule stated above, and yet it risks exposing semi-constructed objects to external code. It’s a minor point but easily overlooked.

This is somewhat anecdotal, but I usually reserve constructors for state essential for the object to be complete and usable. Barring any setter-injection, once the constructor is run, my object should be able to perform the tasks required of it.

Anything that can be deferred, I leave out of the constructor (preparing output values, etc). With this approach, I feel not using constructors for anything but dependency injection makes sense.

This also has the added benefit of hard-wiring your mental design process to not do anything prematurely. You won’t initialize or perform logic that may never end up being used because at best all you’re doing is basic setup for the work ahead.

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa

Can we live without constructors?

Let’s say in some reason all objects are created this way $obj = CLASS::getInstance(). Then we inject dependencies using setters and perform starting initialization using $obj->initInstance(); Are there any real troubles or situations, which can’t be solved, if we won’t use constructors at all?

P.s. the reason to create object this way, is that we can replace class inside getInstance() according to some rules.

I’m working in PHP, if that matter

8

I’d say that this severly hinders your design space.

Constructors are a great place to initialize and validate parameters passed in. If you can no longer use them for that, then initialization, state handling (or plain out denying constructor of “broken” objects) becomes a lot harder and partially impossible.

For example, if every Foo object needs a Frobnicator then it might check in its constructor if the Frobnicator is non-null. If you take away the constructor, then it gets harder to check. Do you check at every point where it would be used? In an init() method (effectively externalizing the constructor method)? Never check it and hope for the best?

While you could probably still implement everything (after all, you’re still turing complete), some things will be a lot harder to do.

Personally I’d suggest looking into Dependency Injection/Inversion of Control. These techniques also allow switching concrete implementation classes, but they don’t prevent writing/using constructors.

3

2 advantages to constructors:

Constructors allow for the an object’s construction steps to be done atomically.

I could avoid a constructor and use setters for everything, but what about mandatory properties as Joachim Sauer suggested? With a constructor, an object owns its own construction logic so as to ensure that there are no invalid instances of such class.

If creating an instance of Foo requires 3 properties to be set, the constructor could take a reference to all 3, validate them and throw an exception if they are invalid.

Encapsulation

By relying solely on setters, the burden is on the consumer of an object to build it properly. There could be different combinations of properties that are valid.

For example, every Foo instance needs either an instance of Bar as property bar or an instance of BarFinder as property barFinder. It can use either one. You can create a constructor for every valid set of parameters and enforce the conventions that way.

The logic and semantics for the objects live within the object itself. It’s good encapsulation.

Yes, you can live without constructors.

Sure, you may end up with a lot of duplicated boiler plate code. And if your application is of any scale, you’ll likely spend a lot of time trying to locate the source of a problem when that boilerplate code isnt used consistently across the application.

But no, you don’t strictly ‘need’ your own constructors. Of course, you don’t strictly ‘need’ classes and objects, either.

Now if your goal is to use some sort of factory pattern for object creation, that isnt mutually exclusive to using constructors when initializing your objects.

2

The advantage of using constructors is that they make it easier to ensure that you will never have an invalid object.

A constructor gives you the opportunity to set all member variables of the object to a valid state. When you then ensure that no mutator method can change the object to an invalid state, you will never have an invalid object, which will save you from a lot of bugs.

But when a new object is created in an invalid state and you must call some setters to put it into a valid state in which it can be used, you are risking that a consumer of the class forgets to call these setters or calls them incorrectly and you end up with an invalid object.

A workaround could be to create objects only through a factory-method which checks every object it creates for validity before returning it to the caller.

$obj = CLASS::getInstance(). Then we inject dependencies using setters and perform starting initialization using $obj->initInstance();

I think you’re making this more difficult than it needs to be. We can inject dependencies just fine through the constructor – and if you have a lot of them, just use a dictionary-like structure so you can specify what ones you want to use:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>$obj = new CLASS(array(
'Frobnicator' => (),
'Foonicator' => (),
));
</code>
<code>$obj = new CLASS(array( 'Frobnicator' => (), 'Foonicator' => (), )); </code>
$obj = new CLASS(array(
    'Frobnicator' => (),
    'Foonicator' => (),
));

And within the constructor, you can ensure consistency like so:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>if (!array_key_exists('Frobnicator', $args)) {
throw new Exception('Frobnicator required');
}
if (!array_key_exists('Foonicator', $args)) {
$args['Foonicator'] = new DefaultFoonicator();
}
</code>
<code>if (!array_key_exists('Frobnicator', $args)) { throw new Exception('Frobnicator required'); } if (!array_key_exists('Foonicator', $args)) { $args['Foonicator'] = new DefaultFoonicator(); } </code>
if (!array_key_exists('Frobnicator', $args)) {
    throw new Exception('Frobnicator required');
}
if (!array_key_exists('Foonicator', $args)) {
    $args['Foonicator'] = new DefaultFoonicator();
}

$args can then be used to set private members as necessary.

When done entirely within the constructor like so, there will never be an intermediate state where $obj exists but is not initialized, as there would be in the system described in the question. It’s better to avoid such intermediate states, because you can’t guarantee the object is always going to be used correctly.

I was actually thinking about similar things.

The question I asked was “What constructor does, and is it possible to do it differently?” I reached those conclusions:

  • It ensures some properties are initialized. By accepting them as parameters and setting them. But this could easily be enforced by compiler. By simply annotating the fields or properties as “required” the compiler would check during creation of the instance if everything is properly set. The call to create the instance would probably be same, there just wouldn’t be any constructor method.

  • Ensures the properties are valid. This could be easily achieved by assert condition. Again you would just annotate the properties with correct conditions. Some languages already do this.

  • Some more complex construction logic. Modern patterns don’t recommend to do that in constructor, but propose using specialized factory methods or classes. So the use of constructors in this case is minimal.

So to answer your question: Yes, I believe it is possible. But it would require some big changes in language design.

And I just noticed my answer is pretty OT.

Yes, you can do nearly everything without using constructors but this is clearly squandering benefits of Object-Oriented Programming languages.

In modern languages (I’ll talk here about C# which I program in) you can limit parts of code that can be run only in a constructor. Thanks to which you can avoid clumsy mistakes. One of such a thing is readonly modifier:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<code>public class A {
readonly string rostring;
public A(string arg) {
rostring = arg;
}
public static A CreateInstance(string arg) {
var result = new A();
A.rostring = arg; // < because of this the code won't compile!
return result;
}
}
</code>
<code>public class A { readonly string rostring; public A(string arg) { rostring = arg; } public static A CreateInstance(string arg) { var result = new A(); A.rostring = arg; // < because of this the code won't compile! return result; } } </code>
public class A {
    readonly string rostring;

    public A(string arg) {
        rostring = arg;
    }

    public static A CreateInstance(string arg) {
        var result = new A();
        A.rostring = arg;  // < because of this the code won't compile!
        return result;
    }
}

As recommended by Joachim Sauer previously instead of using Factory design patter read about Dependency Injection. I would recommend reading Dependency Injection in .NET by Mark Seemann.

Instantiate an object with a type depending on the requirements it is absolutely possible. It could be the object itself, using global variables of the system to return a specific type.

However, have a class in the code that can be “All” is the concept of dynamic type. I personally believe this approach create inconsistency in your code, make the test complexes*, and “the future becomes uncertain” with respect to the flow of the proposed work.

*I am referring to the fact that the tests must consider first the type, second the result you want to achieve. Then you are creating large nested test.

To balance some of the other answers, claiming:

A constructor gives you the opportunity to set all member variables of
the object to a valid state… you will never have an invalid object, which will save you from a lot of bugs.

and

With a constructor, an object owns its own construction logic so as to ensure that there are no invalid instances of such class.

Such statements sometimes imply the assumption that:

If an class has a constructor that, by the time it exits, has put the object into a valid state, and none of the class’s methods mutate that state to make it invalid, then it is impossible for code outside the class to detect an object of that class in an invalid state.

But this is not quite true. Most languages do not have a rule against a constructor passing this (or self or whatever the language calls it) to external code. Such a constructor completely abides by the rule stated above, and yet it risks exposing semi-constructed objects to external code. It’s a minor point but easily overlooked.

This is somewhat anecdotal, but I usually reserve constructors for state essential for the object to be complete and usable. Barring any setter-injection, once the constructor is run, my object should be able to perform the tasks required of it.

Anything that can be deferred, I leave out of the constructor (preparing output values, etc). With this approach, I feel not using constructors for anything but dependency injection makes sense.

This also has the added benefit of hard-wiring your mental design process to not do anything prematurely. You won’t initialize or perform logic that may never end up being used because at best all you’re doing is basic setup for the work ahead.

Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa Dịch vụ tổ chức sự kiện 5 sao Thông tin về chúng tôi Dịch vụ sinh nhật bé trai Dịch vụ sinh nhật bé gái Sự kiện trọn gói Các tiết mục giải trí Dịch vụ bổ trợ Tiệc cưới sang trọng Dịch vụ khai trương Tư vấn tổ chức sự kiện Hình ảnh sự kiện Cập nhật tin tức Liên hệ ngay Thuê chú hề chuyên nghiệp Tiệc tất niên cho công ty Trang trí tiệc cuối năm Tiệc tất niên độc đáo Sinh nhật bé Hải Đăng Sinh nhật đáng yêu bé Khánh Vân Sinh nhật sang trọng Bích Ngân Tiệc sinh nhật bé Thanh Trang Dịch vụ ông già Noel Xiếc thú vui nhộn Biểu diễn xiếc quay đĩa Dịch vụ tổ chức tiệc uy tín Khám phá dịch vụ của chúng tôi Tiệc sinh nhật cho bé trai Trang trí tiệc cho bé gái Gói sự kiện chuyên nghiệp Chương trình giải trí hấp dẫn Dịch vụ hỗ trợ sự kiện Trang trí tiệc cưới đẹp Khởi đầu thành công với khai trương Chuyên gia tư vấn sự kiện Xem ảnh các sự kiện đẹp Tin mới về sự kiện Kết nối với đội ngũ chuyên gia Chú hề vui nhộn cho tiệc sinh nhật Ý tưởng tiệc cuối năm Tất niên độc đáo Trang trí tiệc hiện đại Tổ chức sinh nhật cho Hải Đăng Sinh nhật độc quyền Khánh Vân Phong cách tiệc Bích Ngân Trang trí tiệc bé Thanh Trang Thuê dịch vụ ông già Noel chuyên nghiệp Xem xiếc khỉ đặc sắc Xiếc quay đĩa thú vị
Trang chủ Giới thiệu Sinh nhật bé trai Sinh nhật bé gái Tổ chức sự kiện Biểu diễn giải trí Dịch vụ khác Trang trí tiệc cưới Tổ chức khai trương Tư vấn dịch vụ Thư viện ảnh Tin tức - sự kiện Liên hệ Chú hề sinh nhật Trang trí YEAR END PARTY công ty Trang trí tất niên cuối năm Trang trí tất niên xu hướng mới nhất Trang trí sinh nhật bé trai Hải Đăng Trang trí sinh nhật bé Khánh Vân Trang trí sinh nhật Bích Ngân Trang trí sinh nhật bé Thanh Trang Thuê ông già Noel phát quà Biểu diễn xiếc khỉ Xiếc quay đĩa
Thiết kế website Thiết kế website Thiết kế website Cách kháng tài khoản quảng cáo Mua bán Fanpage Facebook Dịch vụ SEO Tổ chức sinh nhật