|
|
|
|
|
by Thorrez
592 days ago
|
|
>When "out" and "in out" parameters are distinguished, there is no need for the existence of constructors as a separate concept. Any ordinary function with an "out" parameter can be used wherever C++ requires a dedicated constructor. Instead of constructors, it is enough to have an identifier convention for functions that should be called by the compiler when you want implicit initialization or implicit conversions. Why do we need "out" vs "in out" parameters for this? Why can't a function that returns the object work just as well? And "an identifier convention for functions that should be called by the compiler when you want implicit initialization or implicit conversions" seems essentially the same as constructors to me. >Moreover, there is no need to care about "copy" semantics and "move" semantics or about temporaries which are or which are not generated by the compiler. It is easy for the compiler to always choose the best implementation without programmer intervention, when it knows the correct parameter modes for the functions. How would I implement something like std::vector with deep copy and move support of its contained objects without writing copy and move constructors (or operators)? There needs to be code saying "allocate a new block of memory and copy all the elements to that new block", and code saying "just copy the pointer, and set the other pointer to null". Are you saying the implementer would still write that code, just not in constructors/operators? How is that better? |
|
> When "out" and "in out" parameters are distinguished, there is no need for the existence of constructors as a separate concept.
I don't agree with this. You can get I need to do things "post-init" with controlled types, or use a `return X : Thing do ... end return` block. Constructors help ensure invariants. You can make a type `is private` to prevent instantiation, only allowing creation via functions (sort of like Rust `new` associated functions), or initialization via an `out` param. It's OK but not perfect, but you can also tag on a `Type_Invariant` aspect if there are conditions which have to be met by a type. My big problem with Controlled types is that forces a type to be `tagged` (i.e. it has a vtable) which means it affects storage layout of values of that type, which isn't a problem in C++.
You can forbid copies by making something a `limited` type, but you'd have to write your own "Move" equivalent, and some of the containers have `Move` subprograms implemented to transfer contents. Limited types might elide the copy when returned from a function, but it's been a while since I looked at those rules.