【问题标题】:recursive variadic template function call "loses" pointer on second argument type递归可变参数模板函数调用在第二个参数类型上“丢失”指针
【发布时间】:2016-01-28 10:37:51
【问题描述】:

我有一个函数 (GetArgs),它使用可变参数模板对它的参数(每个都是一个指针)进行排序,将每个参数发送到已为每种类型重载的另一个函数 (GetArg) (目前 int & float)。每种类型的重载函数然后在指针处设置值。

它编译得很好,当我用单一类型的许多参数调用函数时,它运行得很好。但是,如果我使用这两种类型(float 和 int),它将运行良好,直到第一次出现第二种类型,因为(据我所知)指针地址为空(调试器中的 0x0)而崩溃。

这是我的函数定义(在 main 中包含的命名空间中声明):

命名空间.h

int GetArg(int iStackPos,int *i);
int GetArg(int iStackPos,float *f);

template<typename tFirst> int GetArgs(tFirst first)
    {
        GetArg(-1,first);
    }

template<typename tFirst, typename... tRest> int GetArgs(tFirst first, tRest... rest)
    {
        int iStackPos = ((sizeof...(rest) + 1) * -1);


        GetArg(iStackPos,first);
        GetArgs((rest)...);

        return 0;
    }

命名空间.cpp

int GetArg(int iStackPos,int *i)
    {
        *i = 1;
    }

int GetArg(int iStackPos,float *f)
    {
        *f = 2.5;
    }

调用以获取 main 中的 args:

运行良好:

int *i1;
float *f1;

namespace::GetArgs(f1,f1,f1,f1); //no use of int

会崩溃:

int *i1;
float *f1;

namespace::GetArgs(f1,i1,f1); //use of int

当 int 先出现后 float 时也是如此。 空指针发生在递归 GetArgs() 调用中,并且发生崩溃是因为重载的 int GetArg() 尝试写入该指针。 iStackPos 用作 lua 堆栈上的位置,因为这意味着它是从 lua 获取参数的包装器。但是我已经用分配 int 1、float 2.5 替换了 lua 代码,因为 lua 代码不是问题。

【问题讨论】:

  • 我没有看到代码有任何问题。你能创建一个显示崩溃的minimal reproducible example 吗?
  • 您将未初始化的指针传递给您的函数,然后取消引用它们*i = 1。您希望 1 存储在哪里?
  • 按照@n.m. 的观点,尝试GetArgs(&amp;f1, &amp;i1, &amp;f1);
  • 如果指针指向分配的内存,它就可以工作:ideone.com/aOIuwV
  • @Mouse'nKeyboard 未定义行为是未定义行为

标签: c++ pointers recursion overloading variadic-templates


【解决方案1】:

正如其他人已经建议的那样,您将未初始化的内存传递到您的函数中。这会产生未定义的行为。

此外,您不会在 GetArg 函数和第一个 GetArgs 中返回任何内容。这也会给您带来麻烦。

以及在计算 iStackPos 时结合 size_t 和 int。

【讨论】:

  • 嗯,你正在传递未初始化内存的地址
  • @nicomp 哈!好吧,代码将未初始化的地址传递给可能未初始化或未初始化的内存。 scnr ;-)
猜你喜欢
  • 1970-01-01
  • 2017-03-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-06-29
  • 2018-03-31
  • 2012-02-22
  • 2023-01-10
相关资源
最近更新 更多