简体   繁体   中英

Find a replace a substring C

I am trying to do a find a replace but not just for strings but for substrings also. So the program I am working on looks for the word "bar" and append "foo" in front of any instance of "bar". So my approach is that instead of actually appending the string, I replace the whole string "bar" with "foobar". The code I have right now (not fully tested), should find and replace all occurrences of "bar" with "foobar". However, if there is a string that looks like "bar123abc", it does not replace it with "foobar123abc".

This is the code I have:

static void replaceAllString(char *buf, const char *orig, const char *replace)
{
    int olen, rlen;
    char *s, *d;
    char *tmpbuf;

    if (!buf || !*buf || !orig || !*orig || !replace)
        return;

    tmpbuf = malloc(strlen(buf) + 1);
    if (tmpbuf == NULL)
        return;


    olen = strlen(orig);
    rlen = strlen(replace);

    s = buf;
    d = tmpbuf;

    while (*s) {
        if (strncmp(s, orig, olen) == 0) {
            strcpy(d, replace);
            s += olen;
            d += rlen;
        }
        else
            *d++ = *s++;
    }

    *d = '\0';

    strcpy(buf, tmpbuf);
    free(tmpbuf);
}

Here's how I might do it:

static char *replaceAll(char *buf, int buflen, const char *orig, const char *replace) {
    if (!buf || !*buf || !orig || !*orig || !replace) return buf;

    int olen = strlen(orig), rlen = strlen(replace);

    int max = strlen(buf) + 1;
    if (olen < rlen) {
        max = rlen * ((max / olen) + 1) + 1;
    }
    char *tmpbuf = malloc(max);
    char *bp = buf, *tp = tmpbuf, *sp;

    while (NULL != (sp = strstr(bp, orig))) {
        int f = sp - bp;
        memmove(tp, bp, f);
        memmove(tp + f, replace, rlen);
        tp += f + rlen;
        bp += f + olen;  // no recursive replacement
    }
    strcpy(tp, bp);
    strncpy(buf, tmpbuf, buflen);
    free(tmpbuf);
    return buf;
}

char haystack[128] = "123bar456bar7ba8ar9bar0";

int main(int ac, char *av[]) {
    printf("%s\n", replaceAll(haystack, sizeof haystack, "bar", "foobar"));
}

Note: passing buflen is NOT optional! You DO NOT write to memory buffers you don't know the length of. If I'm interviewing C programmers, this would be an instant "no hire". tmpbuf is allocated the length max , crudely calculated for the worst case (something like "barbarbar"). The heavy lifting here is done by strstr() .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM