이 기능이 더 안전 할 수 있습니까? 팁과 생각을 찾고 있습니다!

StackOverflow https://stackoverflow.com/questions/1077479

  •  21-08-2019
  •  | 
  •  

문제

이것은 다소 이상한 질문입니다.

나는 c 함수를 썼다. 그것의 'like'strchr / strrchr. 그것은 c- 스트링에서 캐릭터를 찾아야하지만 뒤로 가고 포인터를 반환해야합니다. C 문자열이 "Null Intared"가 아니기 때문에 세 번째 매개 변수 '수'가 필요하므로 뒤로보아야 할 숯의 수를 나타냅니다.

/*
*s: Position from where to start looking for the desired character.
*c: Character to look for.
*count: Amount of tests to be done
*
* Returns NULL if c is not in (s-count,s)
* Returns a pointer to the occurrence of c in s.
*/
char* b_strchr(const char* s,int c,size_t count){

    while (count-->0){

        if (*s==c) return s;
        s--;
     }
     return NULL;
}

나는했다 약간 그것에 대해 테스트하지만 그 안에 결함이 있습니까? 보안 문제가 있습니까? 개선 사항이 있습니까? 개선 될 수 있습니까? 그리고 더 중요한 : 이것은 나쁜 생각입니까?

일부 사용.

    char* string = "1234567890";

    printf("c: %c\n",*b_strchr(string+9,'5',10));//prints 5

    printf("c: %c\n",*b_strchr(string+6,'1',7));//prints 1

편집 : 새로운 인터페이스, 일부 변경.

/*
* from:  Pointer to character where to start going back.
* begin: Pointer to characther where search will end.
*
* Returns NULL if c is not between [begin,from]
* Otherwise, returns pointer to c.
*/
char* b_strchr(const char* begin,int c,const char* from){


    while (begin<=from){

        if (*from==c) return from;
        from--;
     }
     return NULL;
}
도움이 되었습니까?

해결책

편집에는 더 좋지만 인터페이스는 여전히 놀랍습니다. 나는 그것을 넣었다 begin 매개 변수 (the 커다란 건초 더미 첫 번째 매개 변수로서 검색되는 것 c 매개 변수 (the 바늘 ) 두 번째로 검색되고 있습니다 from 매개 변수 (검색의 시작 위치) 세 번째. 그 순서는 상당히 큰 API 세트에서 관용적 인 것 같습니다.

다른 팁

코드에는 난해한 인터페이스가 있습니다. 문자열의 마지막 문자와 문자열의 길이를 포인터로 전달합니다. 그것은 그것을 사용하는 문제로 이어질 것입니다.

(또는 코드에는 버그가 있습니다. 루프 앞에 s count를 추가해야합니다.)

시작이 출신이면 현재 코드는 항상 시작되며 원하는 것이 아닙니다. 루프 후 코드는 널 리턴 될 수 있습니다. 그리고 시작 대신! = 루프 조건에서 시작하여 시작을 사용합니다. <그렇지 않으면 누군가가 매개 변수의 순서를 혼합 할 때 포인터 산술 오버플로를 사용합니다.

편집 : 두 번째 생각에 당신이 [시작,부터 시작하기 때문에] 시작해야합니다. 시작해야합니다.

나는 c 함수를 썼다. 그것의 'like'strchr / strrchr.

당신은 재창조하려고 시도했습니다 strrchr(), 그렇지 않습니다 strchr().

그 안에 결함이 있습니까?

예. 몇몇의. :-(

부터 b_strchr() 돌아올 수 있습니다 NULL, 당신은 그것을 직접 넣어서는 안됩니다 printf() 성명. 연기 NULL 일반적으로 segfault가 발생합니다.

좋아하는 변형으로 더 나을 수 있습니다.

char *result;

result = b_strchr(string + 9, 'a', 10));
if (result == NULL)
{
    printf("c: NULL\n");
}
else
{
    printf("c: %c\n", *result);
}

또한 언제

(count >= length of the input string) and the character is not found

당신은 예측할 수없는 결과를 얻을 것입니다 s 더 이상 문자열의 캐릭터를 가리키지 않습니다. s 문자열이 시작되기 전에 메모리를 가리키고 있습니다. 예를 들어 시도하십시오

result = b_strchr(string + 9, 'a', 11));
if (result == NULL)
{
    printf("c: NULL\n");
}
else
{
    printf("c: %c\n", *result);
}

그리고 무슨 일이 일어나는지보십시오.

사용 테스트 사례를 확장하여 성공적으로 작동 할 수있는 외부의 조건을 포함하십시오. 코드를 실제로 테스트 할 테스트 케이스를 설계하도록 도와달라고 다른 사람에게 요청하십시오.

그리고 더 중요한 : 이것은 나쁜 생각입니까?

학습 운동으로서 절대적으로 그렇지 않습니다.

그러나이 경우 생산 코드의 경우 표준을 고수하는 것이 좋습니다. strrchr().

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top