【问题标题】:Delete chars from string C从字符串 C 中删除字符
【发布时间】:2014-05-15 13:31:03
【问题描述】:

所以我从一本书开始学习 C,其中一个练习是创建一个函数,该函数将采用 2 个字符串并从第一个字符串中删除第二个字符串中的字符。

我们 stile 没有了解指针,所以我想没有它们也是可能的, 但是当我尝试运行我的代码时,它的迷恋。

代码:

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

char squis(char string[], char sub[])
{
    int i, c;
    char ret_string[strlen(string)];
    int map[strlen(string)];
    for(i=0; i<= strlen(string);i++)
        map[i] = -1;
    for(i=0; i<= strlen(sub);i++)
    {
        while(string[c]!='\0')
        {
            if (string[c]==sub[i])
                map[c] = c;
            c++;
        }
        c=0;
    }
    for(i=0; i<= strlen(string);i++)
    {
        if (map[i]==-1)
            ret_string[c++] = string[i];
    }
    ret_string[c] ='\0';
    return ret_string[0];
}

int main()
{
    char string[] = "string";
    char remove[] = "sasas";
    printf("%s",squis(string,remove));
    return 0;
}

我是 C 的新手,所以我认为问题在于我对 C 的工作方式缺乏了解。

非常感谢您的帮助:-)

更新:似乎问题在于函数末尾的返回。 当我在函数内部打印ret_string 时,该函数似乎运行良好(除了一个使函数忽略子字符串中的第一个字符的错误,但我稍后会处理它),但是当我尝试返回数组时在主函数中打印它失败。

C中返回数组有具体的规则吗?

【问题讨论】:

  • 不要忘记字符串中终止 '\0' 的空间。
  • 在我的头上 - i&lt;= strlen(string) 仔细检查这个..检查索引是如何在 C 中完成的
  • 尽量不要将太多的命令放在一行中,使用临时变量,学习使用 debuffer 并使用它来跟踪您的代码,逐步检查所有相关变量,以发现真正发生的事情。
  • 看看你的squis 例程返回——它不是一个字符串,即使你告诉你的程序它是一个(通过在printf 中请求%s)。
  • 另外,"%s" 需要一个指向char 的指针,即char*char 的数组,如果传递给printf(),它将衰减为一个指针)而不是@987654333 @ 本身。

标签: c string function


【解决方案1】:

这是一个明显的问题:

int map[strlen(string)];
for(i=0; i<= strlen(string);i++)
    map[i] = -1;

您创建一个strlen(string) 字符数组,然后初始化数组中的strlen(string) + 1 字符。越界写入到undefined behavior,任何事情都可能发生。

将循环条件更改为小于&lt;。您可能应该在所有循环中都这样做。

ret_string 也有类似的问题,这将是您返回的字符串。最多为strlen(string) 个字符,但是您需要为字符串终止符添加一个字符,因此数组需要为strlen(string) + 1 长。

那么您遇到的问题是squis 函数只返回单个字符,但在您的printf 调用中您将此单个字符视为字符串。这应该会让你的编译器对你发出警告。如果您通过简单地返回 ret_string 来解决此问题,您将遇到 未定义行为 的另一种情况,因为您随后返回一个指向局部变量的指针,该指针在函数退出时超出范围,因此返回指针不再有效。如果您决定在堆上分配ret_string,则当前调用会发生内存泄漏,因为指针不会被保存,因此您可以释放分配的内存。

【讨论】:

  • 我不明白 strlen() 有什么问题。string[] = "string"; 所以strlen(string))= 6。如果我要创建 string2[6] 0-5 将包含单词 string 而 6 将用于 \0,我错了吗?
  • @OrHalimi 是的,strlen(string) 将返回 6,但是您有一个包含终止符的 7 字符数组。如果你创建一个包含六个字符的数组来保存七个字符,那么我希望你能看到问题所在。
  • 嗬,我明白了。我需要用maloc定义数组吗?那么我的问题就解决了吗?
  • @OrHalimi 对于ret_string,您需要在堆外分配是的,它会解决您的一些问题。
猜你喜欢
  • 2022-01-09
  • 2011-12-10
  • 1970-01-01
  • 2010-12-02
  • 2015-01-13
  • 2012-06-25
  • 2019-11-09
相关资源
最近更新 更多