【问题标题】:Dynamically allocated string from command line argument从命令行参数动态分配的字符串
【发布时间】:2014-10-04 17:58:33
【问题描述】:

我正在寻找使用 C 中的 for 循环处理通过命令行参数传递的字符串。我想知道这是否是正确的方法。

main(int argc, char * argv[])
{
    char * somestring;
    somestring = malloc( (strlen(argv[1]) + 1) * sizeof(char) );
    somestring = argv[1];

       ...
}

如果我这样做了,C 是否会分配适当的内存:

char * somestring;
somestring = argv[1];

【问题讨论】:

  • 为什么不使用strcpy?如果你不要求,为什么 C 会为你分配内存?
  • 视情况而定。您希望能够修改somestring 并保持原始参数不变吗?您只想使用(不修改)参数吗?
  • 我只想用 for 循环逐个字符地处理它。
  • 如果你只是想处理argv[1]元素,可以立即进行,不需要先复制。仅当您想更改它时,才建议进行复制(strcat,甚至更简单:strdup() - 这是 malloc 的副本)
  • malloc 在堆上创建空间来存储它。 strcpy 会将该字符串复制到您分配的位置

标签: c string malloc


【解决方案1】:

如果你想在你自己分配的内存中复制一个参数,那么你必须写

int main(int argc, char * argv[1])
{
    char * somestring;
    somestring = malloc( strlen( argv[1] ) + 1 );
    strcpy( somestring, argv[1] );

       ...
}

否则声明

    somestring = argv[1];

导致内存泄漏。

当不再需要内存时,不要忘记释放内存。

考虑到虽然这条记录

int main(int argc, char * argv[1])

有效最好写

int main(int argc, char * argv[])

因为您指定char * argv[1] 的意图并不明确

【讨论】:

  • 另一方面,如果您不需要副本,则根本不使用 mallocing 并使用 somestring = argv[1] 完全可以。
【解决方案2】:

如果您需要保留临时字符串,那么是的,您需要分配内存,将其复制到新缓冲区(通过strcpy-like 函数),然后释放该缓冲区。

但在这种情况下,命令行参数不是瞬态的。它们在整个过程的生命周期中都可用。因此,只需记住指向它们的指针就足够了。所以这样的事情就足够了:

const char* firstParameter = nullptr;

int main(int argc, char* argv[])
{
    if (argc > 1) firstParameter = argv[1];
}

【讨论】:

    【解决方案3】:

    一个好的方法是为指针分配内存并使用strcpy 函数来复制内容。

    例如:

    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    
    int main(int argc, char * argv[])
    {
        char *somestring;
        if(argv[1] == NULL)
        {
            puts("Argument 1 is not specified.");
            exit(1);
        }
        somestring = malloc( strlen(argv[1])+1 );
        strcpy(somestring, argv[1]);
        printf("%s\n",somestring);
        return 0;
    }
    

    同样在为指针分配内存之前,先检查argv[1]是否不是NULL

    【讨论】:

      【解决方案4】:

      首先,将一个字符串复制到另一个字符串是一种错误的方式。 您已经正确完成了内存分配,但是您将字符串复制到另一个字符串的方法是错误的。您已为字符串分配内存并将其地址收集到某个字符串中。现在您将 argv[1] 分配给它,它是命令行参数向量的地址,实际上是二维数组。所以你应该使用 strcpy() 来复制字符串。

      或者,如果您只想要字符串的基地址,请改用 char 指针并将 argv[1] 分配给它。但是没用。

      附:不建议像您一样传递命令行参数,因为所有参数都存储在参数向量 argv 中,它是二维数组。因此,如果您只传递一个字符串,那没关系,但如果您传递多个字符串,请改用 char **argv。

      【讨论】:

      • argv 是一个 3D 数组是什么意思?从来没有听说过这个想法。另外你似乎没有意识到函数参数char *argv[1]char*argv[]char**argv都是一样的。
      • 但是如果你只将参数存储在 argv[1] 中,那么你将如何使用传递的下一个参数?
      • 您没有在argv[1] 中“存储”参数。您迫切需要阅读如何解释函数的“数组”参数。 C 常见问题解答应该是一个很好的起点。
      • 抱歉,写错了。我没有注意到这一点。它实际上是二维数组。当您传递多个参数时,您如何获得不同的参数?通过取消引用它一次。现在,如果您只想获得第二个参数的第一个字符,您将如何获得呢?通过 argv[1][0] ri8?
      • 还是不对,argv 不是二维数组。它是指向char 的指针。
      猜你喜欢
      • 2022-01-06
      • 2021-12-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-08-19
      • 1970-01-01
      相关资源
      最近更新 更多