1

我正在编写一个需要函数的代码。此函数获取一个字符串作为输入并返回一个字符串。

到目前为止,我的计划是获取一个str[],删除所有$'s 和空格,并将其存储在另一个稍后返回的字符串中:

char *getstring(char str[])
{
    int i=0;
    char rtn[255];
    while (i<strlen(str))
    {
       if (str[i] != " " || str[i] != "$" )
             rtn[i] = str[i];
       else
             rtn[i] = '';
    } 
    return str;
}

我觉得这行不通。有任何想法吗??:-S

4

4 回答 4

2

问题 #1:
您的函数返回一个指向堆栈上分配的(临时)字符串的指针。这意味着一旦你的函数结束,内存rtn就会被释放,这会使char *函数返回的指针无效。

你宁愿做的是:

void getstring(char str[], char rtn[])
{
    /* Some processing on rtn... */
}

调用者getstring应该处理作为rtn.

问题 #2
您的 while 循环将无限期运行,因为i永远不会增加。放在i++循环内的某个地方。

问题 #3
您的if-statement 中的条件有问题。你比较str[i], 这是 a char, to " "or "$", 它们是字符串文字('\0'最后有)。这是错误的。
您需要将它们与用撇号(不是引号)表示的字符进行比较。
另外,请注意测试条件也是错误的。您需要一个逻辑 AND 运算符而不是 OR。将-statement
更改为:if

if (str[i] != ' ' && str[i] != '$')

问题#4
什么rtn[i] = '';意思?''是一个空字符常量,这在 C 中是非法的。
你想跳过一个字符str吗?

问题#5
你有索引问题。因为strandrtn可能显然具有不同的长度,您需要管理两个运行索引,每个字符串一个。

问题 #6
rtn函数返回时不一定以 null 结尾。在函数返回之前(即-loop 结束之后)赋值'\0'给 end 。rtnrtn[i] = '\0';while


这是您的代码,上面提到的所有问题都已修复:

void getstring(char str[], char rtn[])
{
    int i = 0, j = 0;
    while (i < strlen(str))
    {
       if (str[i] != ' ' && str[i] != '$')
             rtn[j++] = str[i];
       i++;
    }
    rtn[j] = '\0';
}

这是一个更有效的版本,它使用指针而不是索引,并且不使用strlen

void getstring(char *str, char *rtn)
{
    while (*str)
    {
       if (*str != ' ' && *str != '$')
             *rtn++ = *str;
       *str++;
    }
    *rtn = '\0';
}
于 2012-06-30T11:17:51.783 回答
1

它绝对行不通。您没有增加 'i' 计数器,并且 '' 的分配不会跳过符号。

就地变体(在速度方面不是最佳的)

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

void getstring(char* str)
{
    int j, i = 0, len = strlen(str);

    while(i < len)
    {
        char ch = str[i];

        if(ch == ' ' || ch == '$')
        {
            /// shift by one
            for(j = i ; j < len + 1; j++) { str[j] = str[j + 1]; }

            len--;
            i--;
        }

        i++;
    } 

    str[len] = 0;
 }

 int main()
 {
      char test_string[] = "Some string $with$ spaces";

      printf("Src = %s\n", test_string);
      getstring(test_string);
      printf("Res = %s\n", test_string);
      return 0;
 }

以及重新分配的变体

char *getstring(const char* str)
{
    int i_src = 0;
    int i_dest = 0;
    int len = strlen(str);

    char* rtn = (char*)malloc(len + 1);

    while (i_src < len)
    {
       char ch = str[i_src];
       if ( (ch != ' ') && (ch != '$') )
       {
            rtn[i_dest] = ch;
            /// increment destination index here
            i_dest++;
       }
       /// increment the source index always
       i_src++;
    } 

    rtn[i_dest] = 0;

    return rtn;
}

稍后不要忘记 free() 结果。

于 2012-06-30T11:21:25.993 回答
0
  1. 如果要从函数返回新字符串,则应为该字符串动态分配内存。在您的代码char rtn[255];中,您在堆栈上分配内存,rtn退出函数后它将被清除。你应该写:

    char *rtn = (char *) malloc(strlen(str));

    当然,您应该继续跟踪内存以防止内存泄漏和调用free()释放内存。

  2. '' 的赋值不会跳过符号,i当您看到不需要的符号时不应增加(并且您错过了代码中的增量)。

  3. 您返回了错误的值,您应该返回rtn而不是str.

正确的代码如下:

char *getstring(char str[])
{
    int i=0, rtn_pos = 0;
    size_t len = strlen(str);
    char *rtn = (char*) malloc(len + 1);
    for (i = 0; i < len; ++i)
       if (str[i] != ' ' && str[i] != '$' )
             rtn[rtn_pos++] = str[i];
    rtn[rtn_pos] = '\0';
    return rtn;
}
于 2012-06-30T11:28:17.023 回答
0

最好让调用者提供目标字符串(调用者可能知道它应该有多大),并返回它不知道的东西:写入 rtn[] 数组的字节数。

size_t mygetstring(char *rtn, char *str)
{
    size_t pos, done;

    for (pos=done=0; rtn[done] = str[pos]; pos++)
    {
       if (rtn[done] == ' ' || rtn[done] == '$' ) continue;
       done++;
    } 
    return done; /* number of characters written to rtn[], excluding the NUL byte */
}
于 2012-06-30T11:51:30.737 回答