4 ms·
It's a lot easier to reason about code if I don't need to worry that something as simple as my_variable = MyType() might be calling out to a database with
by mjr00 2y ago
It's a lot easier to reason about code if I don't need to worry that something as simple as
my_variable = MyType()
might be calling out to a database with invalid credentials, establishing a network connection which may fail to connect, or reading a file from the filesystem which might not exist.
You are correct that you don't want an object that can be half-initialized. In that case, any external resources necessary should be allocated before the constructor is called. This is particularly true if the external resources must be closed after use. You can see my other comment[0] in this thread for a full example, but the short answer is use context managers; this is the Pythonic way to do RAII.
[0] https://news.ycombinator.com/item?id=43736940 https://news.ycombinator.com/item?id=43736940
- rcxdude 2y agoWhy, when my_var = MyType() my_var.actually_init() Works in exactly the same way? Errors get reported the same, it has the same semantics, you have the same need to keep track of things, it's just two lines instead of one and you're more likely to have a partially initialised object floating around. I really don't see the advantage at all. Context managers are handy if you need to guarantee cleanup in simple object lifetimes, and in that case __enter__ is probably the better place to do setup because it's closer to where you get guarantees about the cleanup happening, but context managers are not actually RAII, just a partial substitute.
- mjr00 2y agoYour code is comparing to the wrong alternative; the comparison should be to connection = connect_to_database() my_var = MyType(connection) It's far more testable, maintainable, more explicit about when and which objects are created, and never has a partially initialized object.
- lyu07282 2y ago> might be calling out to a database with invalid credentials, establishing a network connection which may fail to connect, or reading a file from the filesystem which might not exist. In python its not unusual that, import some_third_partylib will do exactly that. I've seen libraries that will load a half gigabyte machine learning model into memory on import and one that sends some event to sentry for telemetry. People write such shit code, its unbelievable.