I originally wanted to make share_obj a class so that I could hide the helper function, but it turned out that I needed a function after all since a function template can be inferred from the parameters but the type cannot from the constructor. By returning a shared_ptr directly, the compiler can do return object optimization.