在c中构建字符串的方法

发布于 2024-12-29 18:16:09 字数 788 浏览 1 评论 0原文

我在这里基于 4 个参数构建一个字符串,并使用 system() 调用它,但我的做法似乎有点混乱。有没有更正确的方法我应该这样做而不是使用所有这些 strcat 和 str1-4?

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

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

    char str1[40] = "sed -n 's/.*\\(";
    char str2[] = "\\)\\(.*\\)\\(";
    char str3[] = "\\).*/\\2/p' ";
    char str4[] = " > ";

    if (argc != 5)
    {
        fprintf (stderr, "Usage %s <LogFile> <token1> <token2> <DumpFile>\n",
                argv[0]);
                exit(EXIT_FAILURE);
    }

    strcat(str1, argv[2]);
    strcat(str1, str2);
    strcat(str1, argv[3]);
    strcat(str1, str3);
    strcat(str1, argv[1]);
    strcat(str1, str4);
    strcat(str1, argv[4]);

    system(str1);

    return 0;
}

I'm building a string here based on 4 arguments and calling it with system(), but seems kinda messy the way i have done it. Is there a more correct way i should have done this and not use all those strcat and str1-4?

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

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

    char str1[40] = "sed -n 's/.*\\(";
    char str2[] = "\\)\\(.*\\)\\(";
    char str3[] = "\\).*/\\2/p' ";
    char str4[] = " > ";

    if (argc != 5)
    {
        fprintf (stderr, "Usage %s <LogFile> <token1> <token2> <DumpFile>\n",
                argv[0]);
                exit(EXIT_FAILURE);
    }

    strcat(str1, argv[2]);
    strcat(str1, str2);
    strcat(str1, argv[3]);
    strcat(str1, str3);
    strcat(str1, argv[1]);
    strcat(str1, str4);
    strcat(str1, argv[4]);

    system(str1);

    return 0;
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(6

颜漓半夏 2025-01-05 18:16:09

您的代码存在一个问题,即您没有检查参数是否适合 40 字节。

我可能会使用 snprintf

snprintf(str, LENGTH, "sed -n 's/.*\\(%s...", argv[2]...);

One problem with your code is that you're not checking the arguments fit in the 40 bytes.

I would probably use snprintf:

snprintf(str, LENGTH, "sed -n 's/.*\\(%s...", argv[2]...);
无悔心 2025-01-05 18:16:09

这节省了重复 strcat() 的二次行为。 OTOH,如果您调用 system(),这些信息就会消失在噪音中。

char str1[4096];
char str0[] = "sed -n 's/.*\\(";

sprintf(str1, "%s%s%s%s%s%s%s%s", str0, argv[2], str2, argv[3], str3, argv[1], str4, argv[4]);

如果您担心缓冲区溢出,您可以使用 snprintf()(您应该担心;str1 中的 40 个字节是不够的;您将 96 留在了末尾,如char str1[4096];)。您可以检查返回值以查看写入了多少个字符。

This saves on the quadratic behaviour of repeated strcat(). OTOH, that is lost in the noise if you call system().

char str1[4096];
char str0[] = "sed -n 's/.*\\(";

sprintf(str1, "%s%s%s%s%s%s%s%s", str0, argv[2], str2, argv[3], str3, argv[1], str4, argv[4]);

You could use snprintf() if you're worried about buffer overflows (and you should be; 40 bytes in str1 is not enough; you left the 96 off the end, as in char str1[4096];). You could check the return value to see how many characters got written.

酷遇一生 2025-01-05 18:16:09

总有 sprintf 会让您的生活更简单。如果使用 sptrintf,请确保缓冲区足够大以容纳结果。还有一个更安全的版本 snprintf 将为您进行边界检查。

There is always sprintf which will make your life simpler. Make sure if you use sptrintf the buffer is large enough for the result. There is also a safer version snprintf which will do the bounds checking for you.

青衫负雪 2025-01-05 18:16:09

唯一的问题是您可能会遇到缓冲区溢出(如果输入太长)。要修复它,请检查字符串的长度(使用 strlen),并分配足够的内存来包含所需的字符串。

分配足够的内存后,您可以使用循环,或让 sprintf 为您完成工作。

The only problem is that you may get buffer overflow (if the input is too long). to fix it, check the length of the strings (using strlen), and allocate enough memory to contain the string you want.

After you allocated enough memory, you can use a loop, or let sprintf do the work for you.

萌︼了一个春 2025-01-05 18:16:09

str1 只有 40 个字节长,并且您向其中附加了太多数据。很可能会发生堆栈溢出。我会这样做:

char buffer[1000]; // Choose a reasonable size
snprintf(buffer, sizeof(buffer),
    "sed -n 's/.*\\(%s\\)\\(.*\\)\\(%s\\).*/\\2/p' %s > %s",
    argv[2], argv[3], argv[1], argv[4]);

str1 is only 40 bytes long, and you're appending too much data to it. An stack overflow is likely to occur. I would do:

char buffer[1000]; // Choose a reasonable size
snprintf(buffer, sizeof(buffer),
    "sed -n 's/.*\\(%s\\)\\(.*\\)\\(%s\\).*/\\2/p' %s > %s",
    argv[2], argv[3], argv[1], argv[4]);
梦醒时光 2025-01-05 18:16:09

如果您希望代码处理任意长的参数,那么您将需要使用malloc动态分配字符缓冲区。

  1. 创建一个局部变量来计算所需的总长度,并使用重复调用 strlen 来计算该长度。
  2. 调用 malloc 并记住为空终止符添加一个字符。
  3. 多次使用 strcpystrcat 来构建字符串。
  4. 调用系统
  5. 调用free(或者如果您的进程即将终止则不要打扰)。

If you want your code to handle arbitrarily long arguments then you will need to allocate the character buffer dynamically with malloc.

  1. Create a local variable to calculate the total length required and use repeated calls to strlen to calculate that length.
  2. Call malloc remembering to add one more character for the null-terminator.
  3. Use strcpy or strcat multiple times to build up the string.
  4. Call system.
  5. Call free (or don't bother if your process is about to terminate).
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文