2016-07-24 39 views
1

我需要将一个常量大小的数组传递给C中的函数,但只能使用该数组的一部分。具体来说,有以下伪码说明我的情况:如何仅将一部分输入数组用于函数?

void my_function(int arr_end,double arr[20]) { 
    Create new array arr_new that contains elements 0 to arr_end or arr 
    Use arr_new 
} 

到目前为止,我试图做到以下几点:

void my_function(int arr_end,double arr[20]) { 
    double arr_new[arr_end+1]; 
    int i; 
    for(i=0;i<=arr_end;i++){ 
     arr_new[i] = arr[i]; 
    } 
    // Now I can do what I want with arr_new 
} 

但我得到的错误:int arr_end expression must have a constant value 。下面是错误的在Visual Studio 2015年社区的截图: enter image description here

我的问题是arr_end不是恒定的(这意味着在不同的时间我想提取的arr不同部分)。

如何才能达到我想要的效果(使arr_new包含arr的一部分)仅适用于基本代码,而不使用malloc或类似的东西?谢谢!

+0

[无法重现。(http://ideone.com/cM8Zfv)确定错误是来自该块的代码抛出? – Downvoter

+0

我认为这与数据类型有冲突,double arr_new和int arr_end – Fil

+0

@Fil数组索引应该是非负整数。不应该在这里比较'arr_new'和'arr_end'。 – ameyCU

回答

0

据我所知问题是,当你创建动态数组然后 唯一的办法是使用malloc来分配空间。然后将其分配给 ,如double arr_new[arr_end+1];arr_end只能是明确的值,例如,1,23,而不是像arr_end这样的变量。它应该是这样的double arr_new[5];

+1

对于旧版本的C(以及所有版本的C++),这是正确的。但是OP可以在更新的版本下编译并获得使用这种可变长度数组的能力。请参阅OP的评论。 –

+0

@underscore_d [我不这么认为](http://stackoverflow.com/questions/9610747/which-c99-features-are-available-in-the-ms-visual-studio-compiler) – Downvoter

+0

@Downvoter “在新版本下编译”的C语言,即使用支持这种语言的编译器。 MS不支持的是这样一个长长的清单,它对我来说完全没有意义。但我指的是你对OP的评论,它有助于清楚地说明这一点。 (伟大的名字,顺便说一句) –

0

使用动态分配。代码:

void foo(int end, double arr[20]){ 
    double* newArr = malloc((end + 1) * sizeof(double)); 
    //now you can use newArr like a normal array 
    //Copy like this 
    for(int i = 0; i < end; i++){ 
     newArr[i] = arr[i]; 
    } 
} 
1

动态大小的数组是不能在较早的Ç版本允许的,所以您可以:

  1. 变化的编译选项,以满足你,让你编译,如果你使用的是IDE这可以取决于IDE。

  2. 分配阵列动态使用malloc或类似的功能,如下所示:

    void my_function(int arr_end,double arr[20]) { double *arr_new = malloc((arr_end+1) * sizeof(arr[0])); int i; for(i=0;i<=arr_end;i++){ // do whatever you need } }

  3. 在栈上分配大小20的阵列,并且只需要使用只是其中的一部分(使用for循环)像这样:

    void my_function(int arr_end,double arr[20]) { double arr_new[20]; int i; for(i=0;i<=arr_end;i++){ //do whatever you need } }

如果您必须只发送你需要的部分,方法2是最好的。

+0

对于您的第三种解决方案,您如何只使用数组的一部分?我需要将它作为一个整体传递给另一个不是我的函数,那么如何将一个数组的一部分传递给该函数呢? –

+1

'在堆上分配一个大小为20的数组'你的意思是_堆栈_,对吧?如果大小已知,将它放在堆上是没有意义的(在这种特定情况下,鉴于它不足以摧毁OP的堆栈,仅适用于那里的学者) –

+0

@space_voyager该函数的签名是什么?或者更好,你是什么意思与_“我需要通过它作为一个整体”_? –

0

显然,问题在于Visual Studio。可变长度阵列(VLAs)的概念是C99标准,而Visual Studio似乎只支持C90。

他们似乎有一个解决办法然而,你可以在这里找到:https://msdn.microsoft.com/en-us/library/zb1574zs(v=vs.140).aspx

+0

该页面没有任何意义。 “以下是您如何使用VLA [...] VLA当前不受支持。”这是什么? –

+0

它下面的代码部分,#pragma行。无法真正帮助它。归咎于MS不支持新标准。 – Magnus

+0

是的,我确实已经阅读了所有东西,但它仍然没有意义。它首先说VLA不被支持,然后声明一个,然后才与它做一些线程相关的东西,这似乎是正交的。我发现的所有其他问题都意味着它无法完成。因此,如果您发现其他情况,则应该扩展您的答案以解释此解决方法的原因。目前,他们的例子看起来不相关。 –

1

首先在my_function参数您声明您收到有大小20(double arr[20])的数组,因为数组如果不知道arr有多少个元素,那么它就会被转换为double* arrsee this),所以您应该仔细地或者您将获得段错误。推荐的方法是将double arr[20]更改为double* arr,并为arr的大小添加另一个参数。例如:

void my_function(const size_t arr_end, double* arr, const size_t arr_size) { 
    ... 
} 

第二你要使用VLAsMSVC只支持C90和沃拉斯我们正在C99加入,所以你需要手动与mallocfree分配内存免费当你使用完。

现在,这里是代码固定:

void my_function(size_t arr_end, double* arr, size_t arr_size) { 
    double* arr_new = NULL; 

    // Allocate enough memory to hold the array 
    arr_new = malloc((arr_end + 1) * sizeof(double)); 

    // Copy arr elements to arr_new 
    for(int i = 0; i <= arr_end; i++){ 
     arr_new[i] = arr[i]; 
    } 

    // Now you can do what you want with arr_new 

    // When you finished using it. 
    free(arr_new); 
} 
相关问题