如何使用sprintf追加字符串?

use*_*646 60 c printf

我正面临着sprintf的一个严重问题.

假设我的代码片段是:

sprintf(Buffer,"Hello World");
sprintf(Buffer,"Good Morning");
sprintf(Buffer,"Good Afternoon");
.
.
.
Run Code Online (Sandbox Code Playgroud)

几百个短跑......

如果我这样做,它会被覆盖.

如何避免使用sprintf覆盖.如果我在最后给出printf,我想看到所有的线条.

小智 101

你需要:

sprintf(Buffer,"Hello World");
sprintf(Buffer + strlen(Buffer),"Good Morning");
sprintf(Buffer + strlen(Buffer),"Good Afternoon");
Run Code Online (Sandbox Code Playgroud)

当然,你需要你的缓冲区足够大.

  • 我在这些方面看到的一个技巧是`#define eos(s)((s)+ strlen(s))`,或者如果你愿意,可以声明一个函数.然后你可以使用`sprintf(eos(Buffer),"Stuff")` (5认同)
  • +1虽然我更喜欢Aeth的解决方案,但它似乎比每次重新计算字符串长度更有效. (3认同)
  • 更简单的是,你可以使用 `sprintf(strchr(s, '\0'), "...")`。 (3认同)
  • 这是指针算法。这就像将字符串的当前长度添加到“缓冲区”的起始地址。此操作对 mbs 和 unicode 字符串不安全。例如,获取 unicode 字符串“Hello”的长度将返回 5,但实际上 *Buffer + 5 * sizeof(wchar_t)* 在这种情况下是必需的 (3认同)

Mat*_*ler 64

int length = 0;
length += sprintf(Buffer+length, "Hello World");
length += sprintf(Buffer+length, "Good Morning");
length += sprintf(Buffer+length, "Good Afternoon");
Run Code Online (Sandbox Code Playgroud)

这是一个对错误有抵抗力的版本.如果您在发生错误时不关心它,只要您可以继续沿着您的快乐方式行事,这将非常有用.

int bytes_added( int result_of_sprintf )
{
    return (result_of_sprintf > 0) ? result_of_sprintf : 0;
}

int length = 0;
length += bytes_added(sprintf(Buffer+length, "Hello World"));
length += bytes_added(sprintf(Buffer+length, "Good Morning"));
length += bytes_added(sprintf(Buffer+length, "Good Afternoon"));
Run Code Online (Sandbox Code Playgroud)

  • 然后你就会发生坏事.为简洁起见,我省略了错误检查. (2认同)

Ole*_*aev 29

为安全起见(缓冲区溢出)我建议使用snprintf()

const int MAX_BUF = 1000;
char* Buffer = malloc(MAX_BUF);

int length = 0;
length += snprintf(Buffer+length, MAX_BUF-length, "Hello World");
length += snprintf(Buffer+length, MAX_BUF-length, "Good Morning");
length += snprintf(Buffer+length, MAX_BUF-length, "Good Afternoon");

  • snprintf的第二个参数是unsigned(size_t),这意味着如果length> MAX_BUF,则MAX_BUF-length将下溢,snprintf将很乐意在缓冲区外写入​​,从而产生缓冲区溢出.请注意,snprintf的返回值等于在有足够空间可用时写入的字节数,而不是真正写入的字节数. (8认同)

Mic*_*urr 12

一个snprintfcat()包装snprintf():

size_t 
snprintfcat(
    char* buf,
    size_t bufSize,
    char const* fmt,
    ...)
{
    size_t result;
    va_list args;
    size_t len = strnlen( buf, bufSize);

    va_start( args, fmt);
    result = vsnprintf( buf + len, bufSize - len, fmt, args);
    va_end( args);

    return result + len;
}
Run Code Online (Sandbox Code Playgroud)


Jee*_*tel 8

使用返回值 sprintf()

Buffer += sprintf(Buffer,"Hello World");
Buffer += sprintf(Buffer,"Good Morning");
Buffer += sprintf(Buffer,"Good Afternoon");
Run Code Online (Sandbox Code Playgroud)

  • 这是最好的解决方案,无需strlen (3认同)
  • 请注意,您还需要保存缓冲区的起始地址以供进一步参考。 (2认同)

Ser*_*gGr 6

你为什么要使用sprintf字符串连接时,有一些方法旨在专门为你所需要的,如strcatstrncat

  • 可能是这个例子很简单,只附加了字符串.问题可以扩展到包括其他类型的格式化数据的情况,其中`strcat`不适用. (12认同)

小智 5

我发现以下方法效果很好。

sprintf(Buffer,"Hello World");
sprintf(&Buffer[strlen(Buffer)],"Good Morning");
sprintf(&Buffer[strlen(Buffer)],"Good Afternoon");
Run Code Online (Sandbox Code Playgroud)

  • `strlen` 周围的 `[...]` ?应该是“(...)”吗? (7认同)

PYK*_*PYK 5

小完整代码示例

仅使用 flat plain stdio标准库

#include <stdio.h>
int main()
    {
    char c[1024];
    int  i=0;

    i+=sprintf(c+i,"We "   );
    i+=sprintf(c+i,"Love " );
       sprintf(c+i,"Coding");

    printf("%s",c);
    }
Run Code Online (Sandbox Code Playgroud)

输出:我们热爱编码