返回包含任何字符但给定字符集的字符串的长度

时间:2010-12-07 17:45:21

标签: c

我需要编写一个函数,它接受两个char *,一个包含一个字符串,另一个包含一组字符,它返回不包含任何字符的字符串的长度。

示例:

LenContainsAnyBut("abc", "def"); // returns 3
LenContainsAnyBut("abc", "b"); // returns 1
LenContainsAnyBut("x", "xyz"); // returns 0
LenContainsAnyBut("", "xyz"); // returns 0

这是我的实施:

unsigned int LenContainsAnyBut(const char *s, const char *search_chars) {
    unsigned int len = 0;

    while (*(s + len) != '\0' {
        for (const char *search_char = search_chars; *seach_char != '\0'; ++search_char) {
            if (*search_char == *(s + len)) {
                return len;
            }
        }

        ++len;
    }

    return len;
}

有什么需要改进的吗?我更喜欢“数组表示法”,即s[0]而不是s + 0,但在此作业中不允许使用。

修改

Sry,不知何故设法完全搞砸我的代码>。<。

6 个答案:

答案 0 :(得分:1)

要改变的一件事是len在代码中总是为0,你应该在while内部的for循环之后增加len。

其他小错误是你在len的声明中缺少't'(unsigned in应该是unsigned int)。

我也相信在for循环中你正在改变指针值本身,这只会使s的第一个字符被测试,当测试s * search_chars的其他字符总是等于“/ 0 “尝试在for循环中使用像len这样的整数

答案 1 :(得分:1)

如果您正在使用8位字符,则可以避免嵌套循环。首先确保sscsearch_chars)类型为unsigned char *(不是普通char *!)然后:

unsigned char set[32] = "";
size_t l=0;
for (; *sc; sc++) set[*sc/8] |= 1U<<*sc%8;
for (; *s; s++) l += 1-(set[*s/8]>>*s%8 & 1);

答案 2 :(得分:1)

发布的代码甚至没有编译,并且通过明显的修复,它将进入一个永恒的循环。

话虽如此,我会使用strchr()编写此函数。

答案 3 :(得分:1)

如果您想改善长字符串和/或长排除集的运行时间,那么您可以尝试利用将字符用作数组索引的功能,并创建一个数组来表示允许的字符集/不允许你的字符串。

如果你创建一个长度为256的数组,为所有元素初始化为1(元素0除外,因为我认为你必须假设它总是被排除,因为没有办法在排除字符串中表示它,因为这是一个C字符串),然后遍历你的排除集字符串,将其中的每个字符转换为无符号(字符在某些系统上签名,但它们需要无符号才能使其工作)并设置由该字符索引的字节到0。

在此结尾处,您有一个查找表,可以让您快速判断字符是否为字符串的结尾,运行时间为O(n + m)而不是O(n * m)。

答案 4 :(得分:0)

使用此作业部分来提高我在C中编程的能力有限。

如果问题有明显的答案,那么道歉,

但代码中的值是len的值随着s中的字符被“测试并传递”而增加

答案 5 :(得分:0)

我只是将其实现为:

#include <string.h>

unsigned int LenContainsAnyBut(const char *s, const char *search_chars)
{
    return strcspn(s, search_chars);
}

......但是,嘿,那只是我;)