指针数组-内存分配

时间:2019-06-01 18:58:10

标签: c arrays pointers malloc

我是新的指针数组(将函数放入数组),并使用malloc为它分配内存。您能帮我这段代码吗?具有功能:int comp_int(int a, int b); int comp_int_abs(int a, int b); int comp_int_length(int a, int b); int comp_int_digits_sum(int a, int b); 并希望将指向这些函数的指针放在指针数组中。首先,要为数组动态分配内存并将函数的指针放入其中。卡在这个地方,我在做什么错了?

int (**funcs)(int, int) = malloc(4*sizeof(int));

if(!*funcs)
{
    printf("Failed to allocate memory");
    return 8;
}

*funcs={add_int, sub_int, div_int, mul_int};

2 个答案:

答案 0 :(得分:4)

首先,为什么要分配动态内存?

如果使用普通数组,事情会变得简单一些:

int (*funcs[])(int, int) = {
    comp_int,
    comp_int_abs,
    comp_int_length,
    comp_int_digits_sum,
};

如果要使用动态分配,则需要注意一些事项。

int (**funcs)(int, int) = malloc(4 * sizeof *funcs);

首先,我们需要分配适当的内存量。通过与已取消引用的指针的大小相乘,我们不必担心动态数组的元素类型。 (但是,如果我们想手动编写类型,它将是sizeof (int (*)(int, int)),而不是代码中的sizeof (int);我们数组的元素是指向函数的指针,而不是整数。)

然后我们检查分配失败:

if (!funcs) {

注意:我们检查指针本身(funcs),而不是代码中的动态数组(*funcs)的第一个元素(可能不存在!)。如果malloc失败并返回NULL,则!*funcs将尝试取消引用空指针,这很可能使程序崩溃。

    fprintf(stderr, "Failed to allocate memory\n");

错误消息转到stderr,而不是stdout。行以'\n'终止。

    return 8;
}

由于这里没有真正的数组,因此不能使用初始化语法。特别是,= {在赋值表达式中无效。

最直接的解决方案是手动分配元素:

funcs[0] = comp_int;
funcs[1] = comp_int_abs;
funcs[2] = comp_int_length;
funcs[3] = comp_int_digits_sum;

这有点容易出错,因为我们必须手动指定每个索引。但是,我们可以将其与上面的“普通数组”代码结合使用:

int (*const funcs_init[])(int, int) = {
    comp_int,
    comp_int_abs,
    comp_int_length,
    comp_int_digits_sum,
};

int (**funcs)(int, int) = malloc(sizeof funcs_init);
if (!funcs) { ... }

memcpy(funcs, funcs_init, sizeof funcs_init);

我们只需照常初始化数组(这里称为funcs_init),然后使用memcpy将内容复制到动态分配的内存中。

答案 1 :(得分:1)

首先,从以下位置更改分配:

int (**funcs)(int, int)=malloc(4*sizeof(*funcs));

*funcs={add_int, sub_int, div_int, mul_int};

更改

funcs[0]=add_int;
funcs[1]=sub_int;
funcs[2]=div_int;
funcs[3]=mul_int;

int (*funcs[4])(int, int)={add_int, sub_int, div_int, mul_int};

带有花括号{的符号只能在初始化时使用,不能在赋值时使用。如果使用数组而不是指针,则可以执行以下操作:

if let urlString = "https://wa.me/\(whatsappPhoneNumber)/?text=Hi. ".addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed), 
    let url = URL(string: urlString), 
    UIApplication.shared.canOpenURL(url) {
        UIApplication.shared.open(url)
}