Reputation:
Is there a more or less standard way to output character strings that contain special characters, such ASCII control codes, in such a way that the output is a valid C/C++ literal string, with escape sequences ?
Example of expected output: This\nis\na\\test\n\nShe said, \"How are you?\"\n
Without care, the output would be
This
is
a\test
She said, "How are you?"
not what want.
Upvotes: 1
Views: 2187
Reputation:
If it helps someone, I have quickly put this together:
void printfe(char* string)
{
for (char c= *string; c; c= *(++string))
{
switch (c)
{
case '\a': printf("\\a"); break;
case '\b': printf("\\b"); break;
case '\f': printf("\\f"); break;
case '\n': printf("\\n"); break;
case '\r': printf("\\r"); break;
case '\t': printf("\\t"); break;
case '\v': printf("\\v"); break;
case '\\': printf("\\\\"); break;
case '\'': printf("\\\'"); break;
case '\"': printf("\\\""); break;
case '\?': printf("\\?"); break;
default: (c < ' ' || c > '~') ? printf("\\%03o", c) : putchar(c); break;
}
}
}
(mind the potential non-portability of c < ' ' || c > '~'
, I wanted to avoid any library reference).
Upvotes: 0
Reputation: 153338
Printing escaped strings clearly is tricky.
Problems include
char
.Hexadecimal escape sequence have no specified limit in length. Octal ones are limited to 3 digits.
void EscapePrint(char ch) {
// 1st handle all simple-escape-sequence C11 6.4.4.4
// The important one to detect is the escape character `\`
// Delete or adjust these 2 arrays per code's goals
static const char *escapev = "\a\b\t\n\v\f\r\"\'\?\\";
static const char *escapec = "abtnvfr\"\'\?\\";
char *p = strchr(escapev, (unsigned char) ch);
if (p && *p) {
printf("\\%c", escapec[p - escapev]);
}
// if printable, just print it.
else if (isprint((unsigned char) ch)) {
fputc(ch, stdout);
}
// else use octal escape
else {
// Use octal as hex is problematic reading back
printf("\\%03hho", ch);
}
}
Pedantic: the octal escape sequence is a problem on rare machines whose char
range exceeds 9 bits. This can be handled with a hex escaped sequences at the string level and not on a char
by char
basis as hex escaped sequences need a limit. Example:
input 2 `char`: \1 A
// v----- intervening space
output text including ": "\\x1" "A"
Upvotes: 1
Reputation: 18410
Depending on what you might be trying to achieve I can suggest the following solution: Just replace any non-printable character with "\xnn" (nn being the ascii code of the character. This would boil down to
void myprint (char *s) {
while (*s) {
printf(isalnum((unsigned char) *s) ? "%c" : "\\%03hho", *s);
s++;
}
}
This will of course not use special abbreviations like \n
(but \x0a
) instead, but this shouldn't be a problem.
Upvotes: 0