如何通过C中的引用将数组指针传递给函数?

时间:2014-10-26 03:01:07

标签: c arrays pointers reference pass-by-reference

#include <stdio.h>
#include <stdlib.h>

void populateArray(char* line, char** cmd){
    printf("INPUT LINE: %s\n", line);
    char *  token    = strtok (line, " ");
    int n_spaces = 0, i;

    /* split string and append tokens to 'cmd' */

    while (token) {
      *cmd = realloc (*cmd, sizeof (char*) * ++n_spaces);

      if (*cmd == NULL)
        exit (-1); /* memory allocation failed */

     *cmd[n_spaces-1] = token;

      token = strtok (NULL, " ");
    }

    /* realloc one extra element for the last NULL */

    *cmd = realloc (*cmd, sizeof (char*) * (n_spaces+1));
    *cmd[n_spaces] = 0;

    /* print the cmd */

    for (i = 0; i < (n_spaces+1); ++i)
      printf ("cmd[%d] = %s\n", i, cmd[i]);
}    

int main (int argc, char* argv[])
{
    char *cmd1 = NULL;
    char * line = "ls -l";
    populateArray(line, &cmd1);
}

我知道C是按值传递但是无论如何都要模仿它通过引用传递?我需要将cmd1传递给populateArray(char * line,char ** cmd)作为参考。我做了一些研究并在C中通过引用传递,看起来我需要做这样的事情: 我试过但仍然无法让它适用于数组指针。

void byreference_func(int* n){
    *n = 20;
}
int main(int argc, char *argv[])
{
    int i = 10;
    printf("before the call the value of i is %d\n", i);
    byreference_func(&i);
    printf("after the call the value of i is %d\n", i);
    return 0;
}

编辑:错误代码

anon@turing:~/csce3613/assign3$ gcc gg.c
gg.c: In function âpopulateArrayâ:
gg.c:6:24: warning: initialization makes pointer from integer without a cast [enabled by default]
gg.c:17:23: warning: assignment makes integer from pointer without a cast [enabled by default]
gg.c:19:13: warning: assignment makes pointer from integer without a cast [enabled by default]
anon@turing:~/csce3613/assign3$ ./a.out
INPUT LINE: ls -l
Segmentation fault (core dumped)

4 个答案:

答案 0 :(得分:0)

cmd1是一个数组。数组无法重新分配。您只能对空指针使用realloc,或者先前调用malloc系列函数返回的指针。

相反,你需要这样做:

int main() 
{
    char *cmd1 = NULL;
    populateArray( line, &cmd1 );
}

然后在您的函数内部,将cmd更改为(*cmd)。它与您的int示例完全相似,除了您在该示例中int的任何位置,您需要将其更改为char *。你在你的int示例中正确地写了*n = 20;,但是你忘了在你的真实代码中这样做。

顺便说一句,如果你在返回之前总是去free,那么你并没有真正填充数组,而且。

答案 1 :(得分:0)

我在您的代码段中找不到line的声明。 愿它成为你烦恼的一部分吗?你还可以添加你得到的错误吗?

答案 2 :(得分:0)

当你这样做的时候 char * line = "ls -l -a";您的line实际上是const char *,而不是char *

你应该做

char *line = strdup("ls -l -a");

或者做

char line[] = "ls -l -a";

(这是有效的,请在这里阅读What is the difference between char s[] and char *s?

strtok()尝试修改您的line,使其不能成为const char*

我不做char *cmd1[64]; 我做了

char **cmd1 = (char**)malloc(sizeof(char*));
cmd1[0] = (char*)malloc(sizeof(char) * 64);

以下是工作代码:http://pastebin.com/TTsTpdgU

答案 3 :(得分:0)

C中的所有字符串都由指针(地址)引用,因此您使用char *作为参数定义在每个函数调用中传递字符串的地址。没有必要像简单的char ** char *那样传递它。要将值返回到main,只需将populateArray声明为char *并返回指向cmd1的指针。

接下来,如图所示,您将line声明为常量字符串文字。为了以你的方式使用它,它应该被声明为一个字符数组。 (例如char line[] = "ls -al")。

至于你的程序逻辑,你正在为你添加的每个字符重新分配一些东西。使用string.h中已提供的几个函数,即strcat,要容易得多。这是一个例子。 (请注意,有许多不同的方法可以执行此操作,但使用cmd而不是calloc分配malloc会初始化一串NULL字符,这会使strcat成为快照并保证结果字符串始终以空值终止。)

更新(我不喜欢第一个)

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define CMDSZ 256

char *populateArray (char *line, char *cmd) /* declare as 'char *' and return pointer */
{
    printf ("\nINPUT LINE: %s\n\n", line);

    char *token = strtok (line, " ");
    int i = 0;

    cmd = calloc (CMDSZ, sizeof (cmd));  /* allocate command string to CMDSZ         */

    while (token)                        /* split string and append tokens to 'cmd'  */
    {
        if (strlen (cmd) > 0)            /* if not first command add space           */
            strcat (cmd, " ");

        strcat (cmd, token);             /* add token to cmd    */

        token = strtok (NULL, " ");      /* get next token      */
    }

    for (i = 0; i < (strlen (cmd)); ++i)        /* print each character in cmd */
        printf ("  cmd[%d] = %c\n", i, cmd[i]);

    printf ("\n  cmd: %s\n\n", cmd);            /* print final command         */

    return cmd;
}

int main () {

    char *cmd1 = NULL;
    char line[ ] = "ls -l -a -x -y -z";

    cmd1 = populateArray (line, cmd1);  /* return a pointer to cmd1                 */

    printf ("In main():\n\n  cmd1: %s\n\n", cmd1);

    if (cmd1) free (cmd1);              /* free memory allocated in populateArray   */

    return 0;
}

注意: int main(....)是一个整数函数 - 它应该返回一个值。

<强>输出:

$ ./bin/poparray

INPUT LINE: ls -l -a -x -y -z

  cmd[0] = l
  cmd[1] = s
  cmd[2] =
  cmd[3] = -
  cmd[4] = l
  cmd[5] =
  cmd[6] = -
  cmd[7] = a
  cmd[8] =
  cmd[9] = -
  cmd[10] = x
  cmd[11] =
  cmd[12] = -
  cmd[13] = y
  cmd[14] =
  cmd[15] = -
  cmd[16] = z

  cmd: ls -l -a -x -y -z

In main():

  cmd1: ls -l -a -x -y -z