Rembourrage en C

J’ai écrit cette fonction qui est supposée faire SsortingngPadRight (“Hello”, 10, “0”) -> “Hello00000”.

char *SsortingngPadRight(char *ssortingng, int padded_len, char *pad) { int len = (int) strlen(ssortingng); if (len >= padded_len) { return ssortingng; } int i; for (i = 0; i < padded_len - len; i++) { strcat(string, pad); } return string; } 

Cela fonctionne mais a des effets secondaires étranges … certaines des autres variables sont modifiées. Comment puis-je réparer cela?

Il peut être utile de savoir que printf effectue un remplissage pour vous, en utilisant% -10s car la chaîne de format remplira le champ de saisie avec 10 caractères de long.

 printf("|%-10s|", "Hello"); 

va sortir

 |Hello | 

Dans ce cas, le symbole – signifie “Aligner à gauche”, le 10 signifie “Dix caractères dans le champ” et le s signifie que vous alignez une chaîne.

Le format de style Printf est disponible dans de nombreuses langues et contient de nombreuses références sur le Web. Voici l’ une des nombreuses pages expliquant les drapeaux de formatage. Comme d’habitude, la page printf de WikiPedia est également utile (principalement une leçon d’histoire sur la diffusion de printf).

Pour ‘C’, il existe une autre utilisation (plus complexe) de [s] printf qui ne nécessite pas de format malloc () ou de pré-formatage lorsque vous souhaitez un remplissage personnalisé.

L’astuce consiste à utiliser les spécificateurs de longueur ‘*’ (min et max) pour% s, plus une chaîne remplie de votre caractère de remplissage jusqu’à la longueur potentielle maximale.

 int targetStrLen = 10; // Target output length const char *mySsortingng="Monkey"; // Ssortingng for output const char *padding="#####################################################"; int padLen = targetStrLen - strlen(mySsortingng); // Calc Padding length if(padLen < 0) padLen = 0; // Avoid negative length printf("[%*.*s%s]", padLen, padLen, padding, myString); // LEFT Padding printf("[%s%*.*s]", myString, padLen, padLen, padding); // RIGHT Padding 

Le "% *. * S" peut être placé avant OU après votre "% s", en fonction du souhait de remplissage à gauche ou à droite.

[####Monkey] <-- Left padded, "%*.*s%s"
[Monkey####] <-- Right padded, "%s%*.*s"

J'ai trouvé que PHP printf ( ici ) supportait la possibilité de donner un caractère de remplissage personnalisé, en utilisant le guillemet simple (') suivi de votre caractère de remplissage personnalisé , dans le format% s.
printf("[%'#10s]\n", $s); // use the custom padding character '#'
produit:
[####monkey]

Vous devez vous assurer que la chaîne d’entrée dispose de suffisamment d’espace pour contenir tous les caractères de remplissage. Essaye ça:

 char hello[11] = "Hello"; SsortingngPadRight(hello, 10, "0"); 

Notez que j’ai alloué 11 octets à la chaîne hello pour tenir compte du terminateur nul à la fin.

L’argument que vous avez passé “Bonjour” se trouve dans la zone de données constantes. Sauf si vous avez alloué suffisamment de mémoire à la chaîne char *, cela dépasse les autres variables.

 char buffer[1024]; memset(buffer, 0, sizeof(buffer)); strncpy(buffer, "Hello", sizeof(buffer)); SsortingngPadRight(buffer, 10, "0"); 

Modifier: corrigé de la stack à la zone de données constantes.

Oh ça va, ça a du sens. Donc j’ai fait ça:

  char foo[10] = "hello"; char padded[16]; strcpy(padded, foo); printf("%s", SsortingngPadRight(padded, 15, " ")); 

Merci!

 #include  #include #include #include using namespace std; int main() { // your code goes here int pi_length=11; //Total length char *str1; const char *padding="0000000000000000000000000000000000000000"; const char *mySsortingng="Monkey"; int padLen = pi_length - strlen(mySsortingng); //length of padding to apply if(padLen < 0) padLen = 0; str1= (char *)malloc(100*sizeof(char)); sprintf(str1,"%*.*s%s", padLen, padLen, padding, myString); printf("%s --> %d \n",str1,strlen(str1)); return 0; } 

La fonction elle-même me semble bien. Le problème pourrait être que vous n’atsortingbuez pas assez d’espace pour que votre chaîne y ajoute autant de caractères. Vous pouvez éviter ce problème à l’avenir en transmettant un argument size_of_ssortingng à la fonction et assurez-vous de ne pas remplir la chaîne lorsque la longueur est sur le point d’être supérieure à la taille.

Une chose qui ne va pas du tout dans la fonction qui forme la question originale dans ce thread, que personne n’a mentionnée, c’est que cela concatène des caractères supplémentaires à la fin du littéral de chaîne qui a été passé en paramètre. Cela donnera des résultats imprévisibles. Dans l’exemple d’appel de la fonction, le littéral de chaîne “Hello” sera codé en dur dans le programme, de sorte que la concaténation à la fin de celui-ci écrasera dangereusement le code. Si vous voulez retourner une chaîne plus grande que l’original, vous devez vous assurer de l’allouer dynamicment, puis de le supprimer dans le code d’appel lorsque vous avez terminé.

 #include  #include  int main(void) { char buf[BUFSIZ] = { 0 }; char str[] = "Hello"; char fill = '#'; int width = 20; /* or whatever you need but less than BUFSIZ ;) */ printf("%s%s\n", (char*)memset(buf, fill, width - strlen(str)), str); return 0; } 

Sortie:

 $ gcc -Wall -ansi -pedantic padding.c $ ./a.out ###############Hello 
 #include #include  void padLeft(int length, char pad, char* inStr,char* outStr) { int minLength = length * sizeof(char); if (minLength < sizeof(outStr)) { return; } int padLen = length - strlen(inStr); padLen = padLen < 0 ? 0 : padLen; memset(outStr, 0, sizeof(outStr)); memset(outStr, pad,padLen); memcpy(outStr+padLen, inStr, minLength - padLen); }