C - 压缩字符的函数

时间:2018-03-05 22:53:52

标签: c arrays memory-management

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

char * compress(char *input, int size){

    char *inputa;
    char compressedString[100];
    inputa = (char*)malloc(sizeof(size));
    snprintf (inputa, size, "%s", input);
    int i = 0;
    int x;
    int counter;

    while(i < size){
        counter = 1;
        x = i;
        while (inputa[x] == inputa[x + 1] && (x+1) < size){
            x++;
            counter++;
        }
        if (i != x){
            i = x;
        }else{
            i++;        
        }
    }
    return inputa;
}

main(){

    char ez[] = "blaablaaa";

    printf("%s \n", compress(ez, sizeof(ez)));
    printf("%s", ez);

    return 0;
}

所以,我试图使这个函数压缩连续的字符(例如"blaablaaa""bla2bla3")。我的思考过程是将inputa[x]放在压缩数组上,旁边是计数器,但我似乎无法使其工作。

2 个答案:

答案 0 :(得分:0)

让我们看看这两行:

java -jar demo.jar

inputa = (char*)malloc(sizeof(size)); snprintf (inputa, size, "%s", input); 的类型为size,因此int是整数的大小,大概为4。

您使用sizeof(size)分配了4个字节。

然后使用snprintf尝试将所有输入(malloc,10字节长)复制到一个只有4个字节长的缓冲区中。

10个字节不适合4字节缓冲区。

我不确定你在那里做什么,但这不正确。

答案 1 :(得分:0)

1)您分配的缓冲区太短:

inputa = (char*)malloc(sizeof(size)); 

它只分配4个字节。 你需要

inputa = (char*)malloc(sizeof(char)*size + 1 )); 

2)你忘了释放分配的内存。

3)算法本身需要改进。代码中的评论:

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

/* reverse:  reverse string s in place */
void reverse(char s[])
{
     int i, j;
     char c;

     for (i = 0, j = strlen(s)-1; i<j; i++, j--) {
         c = s[i];
         s[i] = s[j];
         s[j] = c;
     }
}
/* itoa is not a standard function */ 
/* itoa:  convert n to characters in s */
void itoa1(int n, char s[])
{
     int i, sign;

     if ((sign = n) < 0)  /* record sign */
         n = -n;          /* make n positive */
     i = 0;
     do {       /* generate digits in reverse order */
         s[i++] = n % 10 + '0';   /* get next digit */
     } while ((n /= 10) > 0);     /* delete it */
     if (sign < 0)
         s[i++] = '-';
     s[i] = '\0';
     reverse(s);
}

char * compress(char *input, int size){
   int i = 0;
   int r;          // number of repetitions
   char add[2];    // current character buffer
   char rep[32];   // repetitions buffer
   char c;         // current character    

   char *compr = (char* )malloc(sizeof(char)*size + 1); // memory for the compressed string
   compr[0] = 0;   // terminate the buffer
   add[1] = 0;     // terminate the buffer

    while(i < size){

         c = add[0] = input[i]; // get a character 
         strcat(compr,add);     // add to compr
         r = 1;                 // default number of repetitions is one

         while(1)   // count and add to the string
         {
            if(c == input[i+1] ) 
            {        // find how many characters follows c
                r++; // number of repetition
                i++; // moving along the input buffer
            }
            else
            {
                //  check the r for number of repetitions
                if( r > 1)
                {
                    // there were repetitions:
                    // char * itoa ( int value, char * str, int base );
                    itoa1(r,rep);          // get the number 
                    strcat(compr,rep);     // add  repetition number to the compressed string
                }

                i++;// advance to the next character
                break;
            } // else

         }// while
     } //while

    return compr;
}

int main(void){

    char sg7[] = "BLaaaBBLLaaaaXXXaaY";
    char ez[] = "blaablaaa";
    char *ptr;

    printf("%s \n", ptr = compress(sg7, strlen(sg7) ) );
    printf("%s \n", sg7);
    free(ptr);

    printf("\n");

    printf("%s \n", ptr = compress(ez, strlen(ez)));
    printf("%s \n", ez);
    free(ptr);

    return 0;
}

输出:

BLa3B2L2a4X3a2Y 
BLaaaBBLLaaaaXXXaaY 

bla2bla3 
blaablaaa 

我希望它有所帮助。