On 31/10/2016 04:39, Klemens Morgenstern wrote:
Am 30.10.2016 um 14:21 schrieb Bjorn Reese:
The bp::child object should not execute in the constructor, but rather via operator(). That way we can use the named parameter idiom to build up redirections and similar modifications. For example:
auto compile = bp::child("c++").output(bp::null); compile("main.cpp"); // Executes
+1 for me for that style too.
I personally don't like that approach though it certainly would work. I think it's partly a matter of taste, here's my (C) association:
struct X {int std_in; const char* exe;}; X x{.std_in = 2, exe ="stuff"};
I.e. your setting properties.
Now the problem I see is this: what happens here?
auto compile = bp::child("c++"); compile.output(bp::null); compile("main.cpp"); compile.env({"PATH", "/foo"});
The fourth call should fail (and probably throw), since it's impossible to change the environment after the process has been started. Otherwise that should work as you'd expect. One of the great advantages of this style of construction is that it permits conditionals in a fairly natural fashion: auto compile = bp::child("c++"); if (quiet) compile.output(bp::null); compile.arg("-c"); if (debug) compile.arg("-D_DEBUG"); compile.args("-DFOO", filename); for (auto lib : libraries) compile.arg("-l" + lib); auto child = compile(); or something like that. Or you could have a factory function that returns the un-executed builder to the caller to add additional parameters before finally actually executing it, which aids in composability.
So in order to do that, we'd need a child_builder class, that can be converted, similar to boost.format. I consider this style pre C++11, i.e. before variadics. Now granted: it seems not very C++ish, but it's a very unique problem: most properties are inaccesible after you launched the process, which is the reason they are not members.
Variadics are cool, but they contribute to code bloat, since each unique sequence of parameter types requires generating a new overload, and they require templates, which precludes private implementation. For something like this, using them seems like the wrong style to me, and a fluent builder seems like a better approach. But this path might contain bikesheds. On a related note: given a variable number of arguments in a container, how would I pass this to the existing launch functions? I don't see an example of this in the docs, and this seems like the most common case.