Ответ 1
sprintf(prefix,"%s: %s: %s",argv[0],cmd_argv[0],cmd_argv[1]);
Или snprintf
, чтобы предотвратить переполнение буфера.
Есть ли лучший способ объединить несколько строк вместе в c, кроме нескольких вызовов для strcat() все в строке, например ниже?
char prefix[100] = "";
strcat(prefix, argv[0]);
strcat(prefix, ": ");
strcat(prefix, cmd_argv[0]);
strcat(prefix, ": ");
strcat(prefix, cmd_argv[1]);
perror(prefix);
sprintf(prefix,"%s: %s: %s",argv[0],cmd_argv[0],cmd_argv[1]);
Или snprintf
, чтобы предотвратить переполнение буфера.
snprintf будет лучшим и простым в использовании вариантом, хотя он может быть не "быстрым". Вы не указали, каковы ваши критерии. Простота определенно такова:
snprintf(prefix, sizeof(prefix), "%s: %s: %s", argv[0], cmd_argv[0], cmd_argv[1]);
Я мог бы взять репутацию для этого, но что за черт. Самое худшее, что может случиться, - я кое-что узнаю.
В настоящее время я не использую C, и я обычно не использую строки C-стиля на С++. Но одна из моих идей - написать модифицированный файл strcpy(), который возвращает конец строки:
char* my_strcpy(char*dest, const char* src)
{
while ((*dest = *src++))
++dest;
return dest;
}
Теперь Шлемиэль может принести с собой свое ведро:
char prefix[100] = "";
char* bucket = my_strcpy(prefix, argv[0]);
bucket = my_strcpy(bucket, ": ");
bucket = my_strcpy(bucket, cmd_argv[0]);
bucket = my_strcpy(bucket, ": ");
bucket = my_strcpy(bucket, cmd_argv[1]);
perror(prefix);
Я не тестировал это. Комментарии?
EDIT: Удалена ненужная функция my_strcat()
. Также он оказывается таким же, как stpcpy()
, который, по-видимому, является частью POSIX с 2008 года. См. http://www.manpagez.com/man/3/stpcpy/.
Я бы использовал sprintf()
, как это предполагали другие, но это для полноты:
Если у вас stpcpy()
, вы можете сделать:
char prefix[100] = "";
stpcpy(stpcpy(stpcpy(sptcpy(stpcpy(prefix, argv[0]), ": "),
cmd_argv[0]), ": "), cmd_argv[1]);
perror(prefix);
Удобство с stpcpy()
заключается в том, что оно может быть "закованным", как указано выше. Кроме того, поскольку stpcpy()
возвращает указатель на конец результирующей строки, последующие вызовы stpcpy()
не должны проходить через старые данные снова и снова. Таким образом, он более эффективен, чем несколько strcat()
и, вероятно, более эффективен, чем sprintf()
. stpcpy()
- POSIX: 2008.
Если вы пытаетесь построить строку из других строк (что предлагает ваш пример), вы можете использовать snprintf.
char prefix[100] = "";
snprintf( prefix, sizeof(prefix), "%s: %s: %s", argv[0], cmd_argv[0], cmd_argv[1]);
Если вы пытаетесь сделать конкатенацию существующей строки, где вы не можете использовать подход формата, тогда вы, вероятно, застряли в нескольких вызовах strcat, хотя я бы настоятельно предложил вам рассмотреть используя strncat
и проверяя, чтобы у вас не было переполнения буфера.
вы можете использовать snprintf функция
char prefix[100];
snprintf(prefix, 100, "%s: %s: %s", argv[0], cmd_argv[0], cmd_argv[1]);
Предполагая, что у вас есть char [fixed_size], как размещено, а не char *, вы можете использовать один, творческий макрос, чтобы сделать все это сразу с помощью cout-like ordering, а не с раздельным шрифтом printf формат. Если вы работаете со встроенными системами, этот метод позволит вам исключить большое семейство функций printf, таких как snprintf()
(это также не дает жаловаться на жалобу) и даже не требует malloc()
или любых функций из <string.h>
.
#include <unistd.h> //for write
//note: you should check if offset==sizeof(buf) after use
#define strcpyALL(buf, offset, ...) do{ \
char *bp=(char*)(buf+offset); /*so we can add to the end of a string*/ \
const char *s, \
*a[] = { __VA_ARGS__,NULL}, \
**ss=a; \
while((s=*ss++)) \
while((*s)&&(++offset<(int)sizeof(buf))) \
*bp++=*s++; \
if (offset!=sizeof(buf))*bp=0; \
}while(0)
char buf[100];
int len=0;
strcpyALL(buf,len, argv[0],": ", cmd_argv[0],": ",cmd_argv[1]);
if (len==sizeof(buf))write(2,"error\n",6);
else write(1,buf,len);
Не могли бы вы использовать макрос.
#include <stdio.h>
#include <string.h>
#define a argv[0]
#define b argv[1]
#define c argv[2]
#define strcat1(a,b,c) strcat(prefix, a);\
strcat(prefix, ": ");\
strcat(prefix, b);\
strcat(prefix, ": ");\
strcat(prefix, c);\
perror(prefix);\
int main(int argc, char *argv[]){
char prefix[100] = "";
strcat1(a,b,c);
return 0;
}