如何在C语言中实现string.h的strcmp功能

时间:2017-01-24 18:02:54

标签: c arrays string

我试图实现内部的Modify Headers函数" string.h" C中的图书馆 这就是我所做的:

strcmp

一切都很好,但有些字符串输入的情况并不奏效。举个例子:

int myStrCmp(char str1[], int len1, char str2[], int len2)
{
    int i = 0;
    int stop = 0;
    int cmp = 0;
    for (i = 0; i < len1 && !stop; i++)
    {
        if (str1[i] == str2[i])
        {
            cmp = 0;
        }
        else if (str1[i] > str2[i]) 
        {
            cmp = -1; // gives 1 if string 1 will be appear first in dictionary.
            stop = 1; // stops the loop.
        }
        else
        {
            cmp = 1;  
            stop = 1;
        }
    }
    return cmp;
}

我该如何解决?

2 个答案:

答案 0 :(得分:0)

我假设len1len2分别是str1str2的长度。

您未在代码中使用len2,这会导致逻辑错误,并可能导致崩溃(分段错误)。

按照您的代码,解决方案可能是:

int myStrCmp(char str1[], int len1, char str2[], int len2)
{
    int i = 0;
    int stop = 0;
    int cmp = 0;
    for (i = 0; i < len1 && i < len2 && !stop; i++)
    {
        if (str1[i] > str2[i]) 
        {
            cmp = -1; // gives 1 if string 1 will be appear first in dictionary.
            stop = 1; // stops the loop.
        }
        else if (str1[i] < str[i]
        {
            cmp = 1;  
            stop = 1;
        }
    }

    if (!stop && len1 != len2)
    {
        if (str[i] == '\0')
        {
            cmp = -1;
        }
        else
        {
            cmp = 1;
        }
    }

    return cmp;
}

然后,即使这个代码有效,它的风格也很糟糕(性能很差)。我邀请您看一下strcmp函数的Apple实现:

int strcmp(const char *s1, const char *s2)
{
    for ( ; *s1 == *s2; s1++, s2++)
        if (*s1 == '\0')
            return 0;
    return ((*(unsigned char *)s1 < *(unsigned char *)s2) ? -1 : +1);
}

https://opensource.apple.com/source/Libc/Libc-262/ppc/gen/strcmp.c

答案 1 :(得分:0)

首先,这不是strcmp的工作原理,而不是它返回的值。虽然大多数实现都会给你-1,0和1,但ISO standard说明了这一点:

  

strcmp函数返回一个大于,等于或小于零的整数,因为s1指向的字符串大于,等于或小于s2指向的字符串

这意味着它不必总是-1,0和1。你可以期待任何整数。这使得实现也变得简单。

int mystrcmp(const char *s1, const char *s2)
{
    int diff;

    while(1)
    {
        diff = *s1 - *s2;

        if(*s1 == '\0' || *s2 == '\0')
        {
            break;
        }

        s1 ++;
        s2 ++;
    }

    return diff;
}