T.T.T.
T.T.T.

Reputation: 34513

Is there another way to truncate a string?

char out_file_name[30];  


ogSize = strlen(FileName); //i.e. - FileName_anylength.log (always.log)
ogSize -= strlen(IN_FILE_SUFFIX); //amount of chars before .log

strncpy( out_file_name, FileName, ogSize ); //out_file_name now is FileName_anylength (without the .log)  

Is this the best way to do this?

Also, how do I guard that ogSize doesn't happen to be more than 30 chars as it is coming from user input?

Thank You.

Upvotes: 9

Views: 14898

Answers (7)

radio_electronics
radio_electronics

Reputation: 33

A cleaner but slower implementation might be to fully fill all remaining characters with null characters using memset:

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

int main() {
    char myString[100] = "This is a long string.";

    myString[8] = '\0';

    // Fill the remaining elements after the null terminator with '\0'
    memset(&myString[9], '\0', sizeof(myString) - 9);

    printf("Truncated string: %s\n", myString); // Output: "This is "

    return 0;
}

Might lead to less confusion when using gdb, as gdb might also show the characters after the null character. It is also less prone to bugs when you accidentally try to access elements of the array after the null character.

But I guess just placing the null character at the position where you want to truncate will be fine in most situations.

Upvotes: 0

user411313
user411313

Reputation: 3990

char out_file_name[30];
char *suffix=".log";
size_t IN_FILE_SUFFIX = strlen(suffix);

/* also works, if suffix occurs more than 1 time or never ! */
if( strstr( out_file_name, suffix ) )
  out_file_name[ strlen(out_file_name) - IN_FILE_SUFFIX ] = 0;

or

char out_file_name[30];
char *suffix=".log";
size_t IN_FILE_SUFFIX = strlen(suffix);

/* also works, if suffix occurs more than 1 time or never ! */
if( strstr( out_file_name, suffix ) )
{
  char format[20];
  sprintf( format, "%%.%ds", strlen(out_file_name) - IN_FILE_SUFFIX );
  sprintf( out_file_name, format, out_file_name );
}

Upvotes: 1

skimobear
skimobear

Reputation: 1198

You can insert a null into the string to shorten it. Below the function strstr() is used to find the address of the first occurrence of ".log". After that you can subtract the two addresses from each other to find out the length of the name and where to insert the null.

int main() { 
    char suffix[] = ".log";  
    char filename[] = "FileName_anylength.log";  
    char* end_address = strstr(filename, suffix);  
    filename[end_address-filename] = 0;  
    printf("%s", filename);  
}

Upvotes: 1

AndersK
AndersK

Reputation: 36082

use fgets() to read the string from the user, that way you can specify a max length of the string

char* from = FileName;
char* to   = out_file_name;
int curLen = 0;

do
{
  *to++=*from++
}
while(*from && *from!='.' && ++curLen < ogSize);

*to='\0';

Upvotes: 2

Jerry Coffin
Jerry Coffin

Reputation: 490028

Taking your last question first, ensuring a maximum size is pretty easy. Typically you want to use fgets to read the string. This allows you to specify a maximum length. Alternatively, you can specify a maximum size in a scanf format (e.g., "%29s" or "%29[^\n]"). Note the difference between the two: with fgets you specify the buffer size, but with scanf you specify one less than the buffer size (i.e., the maximum number of characters to read).

As for the first question: yes, there are generally better ways. strncpy is a strange function, originally written for a fairly specific purpose, and (to be honest) should probably be removed from the standard library, because while it seems like it should be useful, it almost never really is.

I'd probably do things a little differently. One possibility would be to use snprintf, something like:

snprintf(
    out_file_name,
    sizeof(out_file_name),
    "%*s",
    strlen(FileName) - strlen(IN_FILE_SUFFIX), FileName);

Upvotes: 2

BillP3rd
BillP3rd

Reputation: 1019

Give this a look:

char *trunc;
char *outfile;

strdup( outfile, FileName );

if ( ((trunc = strstr( out_file_name, ".log" )) != NULL )
 *trunc = '\0';

return ( outfile );  // assumes returning result from function

Upvotes: 2

jkerian
jkerian

Reputation: 17016

With a C-style string, you can just set the character you want to truncate on to \0.

Regarding your second question, basically you check. Or you allocate as much memory as you need, based on the string size (remember to include room for that \0).

Upvotes: 18

Related Questions