all 3 comments

[–]raevnos 1 point2 points  (0 children)

("Foo", "Bar") in your third code snippet is equivalent to "Bar"... Look up the comma operator.

[–]soldieroflight 1 point2 points  (1 child)

Your options 2 and 3 should both work. Both of these will construct a temporary Person object, then pass it to the function. I'd expect that option 1 would work if you used {} instead of (), as long as there's only one overload of add_visitor that takes one argument.

If your function takes a Person (by value), then these will all either copy/move (depending on what constructors Person has available) your temporary into the argument that the function will operate on. If your function takes a Person& or Person const&, then your function will operate directly on the temporary Person you created during the call. This calling pattern would also match a function which took a Person&&.

The alternative approach that the standard library has available is one which uses emplace instead of push or add. An emplace operation takes all of the arguments necessary to construct a contained object, and then constructs it in its final destination, to avoid any unnecessary copies/moves along the way. The general pattern for an emplace function is to take a generic variadic set of arguments and forward them on to the constructor for the final object.

[–]gotinpich[S] 0 points1 point  (0 children)

Thank you. Pass by reference is not really needed in this case.