如何在运行时C++中创建参数列表以将其传递给模板函数(...,Ts &&...值),如在 InsertOrUpdateMutationBuilder 中



我想用C++编程谷歌云扳手。

我使用的api包来自https://github.com/googleapis/google-cloud-cpp.
在代码中https://github.com/googleapis/google-cloud-cpp/blob/main/google/cloud/spanner/samples/samples.cc从第1677ff行可以看到方法";EmplaceRow";从";InsertOrUpdateMutationBuilder";,或者不太简单的";MakeInsertOrUpdateMutation";从1739行到1743行。
向内看
https://googleapis.dev/cpp/google-cloud-spanner/latest/namespacegoogle_1_1cloud_1_1spanner.html
";EmplaceRow";以及";MakeInsertOrUpdateMutation";可以看到。更精确地说,你可以看到";EmplaceRow";
上的示例代码https://googleapis.dev/cpp/google-cloud-spanner/latest/namespacegoogle_1_1cloud_1_1spanner.html#a3451b640c4ee19df694fa0539047fcdc
和";MakeInsertOrUpdateMutation";
上的示例代码https://googleapis.dev/cpp/google-cloud-spanner/latest/namespacegoogle_1_1cloud_1_1spanner.html#aced68ba9bc789f44693ad29962fc6ed6

我的问题是:
我如何创建一个变量(!(参数列表,将它们传递到"EmplaceRow";或在";MakeInsertOrUpdateMutation";作为";Ts&。。。值">
和";变量参数列表";意味着这个";列表";(不是std::list(可以以上述方式用作";Ts&。。。值"-列表

到目前为止,我一直在寻找解决方案,但没有找到合适的解决方案:

  1. 两个模板函数通过使用std::tuple将其元组元素扩展为";Ts&。。。值"-列表
  2. 两个模板函数通过使用std::数组将其数组元素扩展为";Ts&。。。值"-列表

两种溶液都是";漂亮的";但没有用
我希望在运行时处理具有不同列数的不同表,但std::tuple和std::array的大小必须在编译时固定(!(
因此,创建一个";Ts&。。。值"-运行时的列表不能用std::tuple和std::array来解决。

所以。。。如何从std::vector、std::list或其他容器类型创建,这些容器类型可以创建、调整大小并填充";扳手::值-值;Ts&。。。值"-列表以将其传递给";EmplaceRow";或";MakeInsertOrUpdateMutation";。

以下是我将std::元组扩展为";Ts&。。。值"-列表:

template <typename Tuple, std::size_t... I>
int myInsrtOrUpdMutBldEmplaceRowBuild_Tup(confDataProc::processConfigData testA,
Tuple const& tuple,
std::index_sequence<I...>)
{
namespace spanner = ::google::cloud::spanner;
//std::cout << "the second 'myInsrtOrUpdMutBldEmplaceRowBuild_Tup'" << std::endl;
auto client = GoClSp::MakeSampleClient(testA.getProjectID(), 
testA.getInstanceID(),
testA.getDatabaseID());
auto commit = client.Commit(spanner::Mutations{
spanner::InsertOrUpdateMutationBuilder(
testA.getTableName(),
testA.getColumnNamesOfTable())
.EmplaceRow(std::get<I>(tuple)...)
.Build()});
if (!commit)
{
throw std::runtime_error(commit.status().message());
}
return 0;
}
template <typename Tuple>
int myInsrtOrUpdMutBldEmplaceRowBuild_Tup(confDataProc::processConfigData testA,
Tuple const& tuple)
{
//std::cout << "the first 'myInsrtOrUpdMutBldEmplaceRowBuild_Tup'" << std::endl;
int iRetVal = myInsrtOrUpdMutBldEmplaceRowBuild_Tup(testA, 
tuple,
std::make_index_sequence<std::tuple_size<Tuple>::value>());
return iRetVal;
}

这段代码有效,但最大的问题是std::元组的大小必须在编译时已知,并且不能在运行时创建可变大小/长度的元组。在此上下文中,大小/长度是已处理表的列数。

也许这个解决方案对其他(比我更好的(程序员来说是显而易见的,或者可能很难。但无论如何,一个有用的代码剪辑或有用的链接总是受欢迎的。

顺便说一句:
根据我的经验,这与"经典"的变元论点非常不同
我不可能改变方法的行为";EmplaceRow";或";MakeInsertOrUpdateMutation"-如果我有,我想把";Ts&amp;。。。值"-列表到更简单的";std::vectorspanner::值值";。

另一方面:
如果有其他C++函数可以在我不知道的云扳手表中插入或更新表行,请通知我。
我"仅";需要一个在C++中插入或更新表的行的解决方案,我不坚持上面描述的方式。

用AddRow替换EmplaceRow,这样就可以了。

在这里,您无法以实用的方式将运行时参数转换为模板参数。(我无法向你展示如何,但相信我,这里的计划很糟糕;我只是不说"不可能",因为我不喜欢撒谎。(

我发现谷歌的C++文档需要愿意并且能够阅读原始标题,有时还需要阅读源代码。在这里,我找到了定义EmplaceRow的类,并寻找它的作用或替代方法。

CCD_ 3在C++语言中的意思是";完美向前进入存储";;通常附近有一种不完美的转发方法(如push_backemplace_back(,用于模板阻碍时。

最新更新