在C中递归地查找给定字符串中的最后一个字符

时间:2015-04-10 16:46:59

标签: c recursion

我试图在递归中找到给定字符串中最后一个字符。我已经编写了第一次出现的代码。我怎么写最后一次?这是我第一次出现的代码:

而不是放弃投票,请提出想法????

#include <stdio.h>

int first_occurance(const char *s,char ch);

int main()
{

    int x;
    x = first_occurance("testtest", 'e');
    printf("%d\n", x );

    return 0;
}
int first_occurance(const char *s,char ch)
{
    int check;
    if (*s == '\0') {   // at null character stop it
        return -1;
    }
    else if (*s == ch) { // match the specified char return
        return 0;
    }
    else {
        check = 1 + first_occurance(s + 1, ch); // else try next char
        if (check == 0) // not matching sum of check will be zero -1 + 1
            return -1;
        return check;   // return index
    }

}

上次出现的例子

string是:testtest

返回值为:5

6 个答案:

答案 0 :(得分:1)

评论strchr()后,我发现了一个由bluepixy编写的代码。然而,为什么人们选择投票而不是帮助呢?

#include <stdio.h>

char *StrrchrR(const char *s, int c, char *find){
    if(s==NULL) return NULL;
    if(*s == '\0') return (c == '\0') ? (char*)s : find;
    return StrrchrR(s + 1, c, *s == c ? (char*)s : find);
}

char *Strrchr(const char *s, int c){
    return StrrchrR(s, c, NULL);
}
/*
char *Strrchr(const char *s, int c){
    char *ret;
    if(s == NULL)return NULL;
    if(*s=='\0') return (c == '\0') ? (char*)s : NULL;
    if(ret = Strrchr(s + 1, c)) return ret;
    if(*s == c) return (char*)s;
    return NULL;
}
*/    
int main(void){
    const char *str = "abcabdefg";
    char *cp;

    cp=Strrchr(str, '\0');
    printf("%c\n", *--cp);//g
    cp=Strrchr(str, 'b');
    printf("%c\n", *++cp);//d
    cp=Strrchr(str, 'z');
    if(!cp)printf("NULL\n");//NULL
    return 0;
}

答案 1 :(得分:1)

抓住最佳解决方案! :)

#include <stdio.h>

int last_occurence( const char *s, char c )
{
    if ( !*s ) return -1;

    int n = last_occurence( s + 1, c );

    return n + ( n != -1 || *s == c );
}

int main(void)
{
    const char *s =  "testtest";
    const char *p;

    for ( p = s; *p; ++ p )
    {
        printf( "%d\n", last_occurence( s, *p ) );
    }

    return 0;
}

程序输出

7
5
6
7
7
5
6
7

函数中的替代return语句可能类似于

return ( *s == c || n != -1 ) ? n + 1 : -1;

如果你想要函数返回指针那么它可以看起来如下

#include <stdio.h>

char * last_occurence( const char *s, char c )
{
    if ( !*s ) return NULL;

    char *p = last_occurence( s + 1, c );

    if ( p == NULL && *s == c ) p = ( char * )s;

    return p;
}

int main(void)
{
    const char *s =  "testtest";
    const char *p;

    for ( p = s; *p; ++ p )
    {
        printf( "%d\n", last_occurence( s, *p ) - s );
    }

    return 0;
}

输出与上面相同

7
5
6
7
7
5
6
7

答案 2 :(得分:0)

搜索char时会发现c == 0时发生的情况。以下处理所有char值。

char *Strrchr(const char *s, int c) {
  while (*s != c) {
    if (*s == 0) {
      return NULL;
    }
    s++;
  }
  // Could there be more?
  if (c) {
    char *p = Strrchr(s + 1, c);
    if (p) {
      return p;
    }
  }
  return (char *) s;
}

某些流水线平台速度更快,分支可能性更少:

char *Strrchr_times(const char *s, int c) {
  while (*s * (*s - c)) {  // only 1 test
    s++;
  }
  // Could there be a later match?
  if (*s) {
    char *p = Strrchr_times(s + 1, c);
    if (p) {
      return p;
    }
  }
  return *s == c ? (char *) s : NULL;
}

由于除了练习之外没有理由进行递归,因此下面是非递归解决方案。

char *Strrchr_nonrecursive(const char *s, int c) {
  const char *p = NULL;
  do {
    if (*s == c) {
      p = s;
    }
  } while (*s++);
  return (char *) p;
}

答案 3 :(得分:0)

三种解决方案!我希望有一个解决你的问题!

如果你只搜索最后一个你可以使用strrchr,但我想你想要所有的出现!如果您需要最后一次出现的位置,您可以使用值strrchr返回值和字符串指针之间的差值来计算它!

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

int strchrpos(char *sd, int lp, char s);
int strchrpos2(char *sd, char s);

int strchrpos(char *sd,int lp, char s)
{
    sd+=(++lp);
    while(*sd!=0 && *sd!=s) {
        sd++;lp++;
    }

    return (*sd!=0)?lp:-1;
}

int strchrpos2(char *sd, char s)
{
    static int lp;

    if (sd==NULL) {
    lp=-1;
    return 0;
    }

    sd+=(++lp);
    while(*sd!=0 && *sd!=s) {
        sd++;lp++;
    }

    return (*sd!=0)?lp:-1;
}

int main(void)
{
    char str[20],* app;
    int p=-1;

    strcpy(str,"testtest");

    puts("searching: s -----------------------------");
    /* If you need ordinal position! */
    while((p=strchrpos(str,p,'s'))>=0)
        printf("%d %s\n",p,str+p);

    puts("searching: t -----------------------------");
    /* if you need the pointer to the substring (std strchr) */
    app=str;
    while( (app=strchr(app,'t'))!=NULL ) {
        printf("%s\n",app);app++;
    }

    puts("searching: t -----------------------------");
    /* If you need ordinal position and you want the
       called function keeps position trace */
    strchrpos2(NULL,0); /* NULL is used as reset */
    while((p=strchrpos2(str,'t'))>=0)
        printf("%d %s\n",p,str+p);

    puts("searching: e -----------------------------");
    /* If you need ordinal position and you want the
       called function keeps position trace */
    strchrpos2(NULL,0); /* NULL is used as reset */
    while((p=strchrpos2(str,'e'))>=0)
        printf("%d %s\n",p,str+p);

    return 0;
}

该计划的输出如下:

searching: s -----------------------------
2 sttest
6 st
searching: t -----------------------------
testtest
ttest
test
t
searching: t -----------------------------
0 testtest
3 ttest
4 test
7 t
searching: e -----------------------------
1 esttest
5 est

记住:

函数strchrpos:第一次调用它时必须接收lp = -1(最后一个位置)。

函数strchrpos2:此函数在解析另一个字符串时不能用于解析字符串,因为字符串跟踪方法基于使用“static int lp” 在函数内部。

答案 4 :(得分:0)

这是C ++代码,而不是使用C样式字符串,我使用C ++字符串,但想法是一样的。 不要使用这个“int check”;额外的变量,因为它可能会给出错误的结果。

int indexOf (string s, char c) {

    if (s == "") {
        return -1;
    } else if (s [0] == c) {
            return 1+indexOf(s.substr(1,s.length()),c);
        } else {
        int subIndex = indexOf(s.substr(1,s.length()),c);
           if (subIndex == -1) {
                return -1;
            } else {
                return subIndex+1;
            }
        }

}

我在字符串中调整了第一次出现的字符。这solution

答案 5 :(得分:-1)

char myversion_strrchr(char *input,char sub)
{
  

想法是检查输入字符串是否为空

     

如果没有,则检查它是否包含sub

     

我们在输入字符串中获取sub的点,我们将当前输入字符串存储在temp变量中,然后继续检查字符串的其余部分是否出现sub

     

如果字符串的其余部分包含sub,则ret_val将存储该字符。并且在每个点我们返回ret_val,如果它不是NULL,否则返回temp;

    char *temp=NULL,*ret_val=NULL;
    if(input[0]=='\0') //check if input string is NULL
        return temp;
    else if(input[0]==sub) // otherwise check if input string starts with sub
        temp=input;// if it does, then store it in a temp variable
    else
        temp=NULL; //if not,then temp variable should be NULL
    ret_val=myversion_strrchr(input+1,sub); //with the rest of the string check if a sub occurs anywhere
    if (ret_val!=NULL) //if a sub occurs in the rest of the string then return that string
        return ret_val;
    else//else,return temp... temp will contain either input string if it starts with sub or it will contain NULL
        return temp;           

}