OpenCV 튜토리얼을 공부하고 assert
기능을 접했습니다 . 무엇을합니까?
OpenCV 튜토리얼을 공부하고 assert
기능을 접했습니다 . 무엇을합니까?
답변:
assert
인수가 거짓으로 판명되면 프로그램 (일반적으로 assert 문을 인용하는 메시지와 함께)을 종료합니다. 예상치 못한 조건이 발생하면 프로그램이 더 확실하게 실패하도록 디버깅하는 동안 일반적으로 사용됩니다.
예를 들면 다음과 같습니다.
assert(length >= 0); // die if length is negative.
다음과 같이 실패한 경우 표시 할보다 유용한 메시지를 추가 할 수도 있습니다.
assert(length >= 0 && "Whoops, length can't possibly be negative! (didn't we just check 10 lines ago?) Tell jsmith");
또는 이와 같이 :
assert(("Length can't possibly be negative! Tell jsmith", length >= 0));
릴리스 (비디 버그) 빌드를 수행 할 때 일반적으로 컴파일러 스위치를 사용 assert
하여 NDEBUG
매크로 를 정의하여 명령문 평가의 오버 헤드를 제거 할 수도 있습니다 . 이것의 결과는 프로그램이 어설 션 매크로 실행에 의존 해서는 안된다는 것 입니다.
// BAD
assert(x++);
// GOOD
assert(x);
x++;
// Watch out! Depends on the function:
assert(foo());
// Here's a safer way:
int ret = foo();
assert(ret);
abort ()를 호출하고 아무것도하지 않는 프로그램의 조합에서, 주장은 사용자가 문자 대신 숫자를 입력하는 것보다는 개발자가 가정 한 것을 테스트하는 데만 사용해야합니다. 다른 방법으로 처리).
assert
일반적으로 예외가 발생합니다"– C ++에서는 "예외"가 발생하지 않으며 중단이라고 부릅니다. 조금 다릅니다.
#
문자는 주석을 나타내지 않습니다.
assert("error message", expression)
어설 션 컴퓨터 문은 문 유사 확인 영어있다.
보세요
많은 컴파일러가 assert () 매크로를 제공합니다. assert () 매크로는 매개 변수가 TRUE를 평가하면 TRUE를 리턴하고 FALSE를 평가하면 어떤 조치를 취합니다. 많은 컴파일러가 실패한 assert ()에서 프로그램을 중단합니다. 다른 사람들은 예외를 던질 것입니다
assert () 매크로의 강력한 기능 중 하나는 DEBUG가 정의되지 않은 경우 전처리 기가 코드를 전혀 축소하지 않는다는 것입니다. 개발 과정에서 큰 도움이되며 최종 제품이 출시 될 때 프로그램의 실행 가능한 버전의 크기가 증가하거나 성능이 저하되지 않습니다.
예 :
#include <stdio.h>
#include <assert.h>
void analyze (char *, int);
int main(void)
{
char *string = "ABC";
int length = 3;
analyze(string, length);
printf("The string %s is not null or empty, "
"and has length %d \n", string, length);
}
void analyze(char *string, int length)
{
assert(string != NULL); /* cannot be NULL */
assert(*string != '\0'); /* cannot be empty */
assert(length > 0); /* must be positive */
}
/**************** Output should be similar to ******************
The string ABC is not null or empty, and has length 3
assert () 함수는 프로그램 버그를 진단 할 수 있습니다. C에서는에 정의되어 <assert.h>
있고 C ++에서는에 정의되어 <cassert>
있습니다. 프로토 타입은
void assert(int expression);
인수 표현식은 변수 또는 C 표현식과 같이 테스트하려는 것이 될 수 있습니다. expression이 TRUE로 평가되면 assert ()는 아무 작업도 수행하지 않습니다. expression이 FALSE로 평가되면 assert ()는 stderr에 오류 메시지를 표시하고 프로그램 실행을 중단합니다.
assert ()를 어떻게 사용합니까? 프로그램 버그 (컴파일 오류와는 구별됨)를 추적하는 데 가장 자주 사용됩니다. 버그는 프로그램 컴파일을 방해하지는 않지만 잘못된 결과를 주거나 부적절하게 실행됩니다 (예 : 잠금). 예를 들어, 작성중인 재무 분석 프로그램이 때때로 잘못된 답변을 제공 할 수 있습니다. 이 변수는 Interest_rate 변수가 음수 값을 취하여 발생하는 것으로 의심되며 절대 발생하지 않아야합니다. 이것을 확인하려면 진술서를 넣으십시오.
주장 (관심 _>> 0); interest_rate가 사용되는 프로그램의 위치에서 변수가 음수가되면 assert () 매크로가 경고합니다. 그런 다음 관련 코드를 검사하여 문제의 원인을 찾을 수 있습니다.
assert () 작동 방식을 보려면 아래 샘플 프로그램을 실행하십시오 . 0이 아닌 값을 입력하면 프로그램이 값을 표시하고 정상적으로 종료됩니다. 0을 입력하면 assert () 매크로가 비정상적인 프로그램 종료를 강제합니다. 표시되는 정확한 오류 메시지는 컴파일러에 따라 다르지만 일반적인 예는 다음과 같습니다.
어설 션 실패 : x, 파일 list19_3.c, 13 행 assert ()가 작동하려면 프로그램을 디버그 모드로 컴파일해야합니다. 디버그 모드 활성화에 대한 정보는 컴파일러 설명서를 참조하십시오 (순간 설명 참조). 나중에 릴리스 모드에서 최종 버전을 컴파일하면 assert () 매크로가 비활성화됩니다.
int x;
printf("\nEnter an integer value: ");
scanf("%d", &x);
assert(x >= 0);
printf("You entered %d.\n", x);
return(0);
정수 값을 입력하십시오 : 10
10을 입력했습니다.
정수 값을 입력하십시오 : -1
오류 메시지 : 비정상적인 프로그램 종료
오류 메시지는 시스템과 컴파일러에 따라 다를 수 있지만 일반적인 아이디어는 동일합니다.
'예외 발생'및 '실행 중지'와 같은 것은 대부분의 컴파일러에 해당 될 수 있지만 모두에게 해당되는 것은 아닙니다. (BTW, 실제로 예외를 던지는 주장 진술이 있습니까?)
c6x와 다른 TI 컴파일러가 사용하는 흥미롭고 약간 다른 어설 션의 의미는 다음과 같습니다. 특정 어설트 명령문을 볼 때 이러한 컴파일러는 해당 명령문의 정보를 사용하여 특정 최적화를 수행합니다. 사악한.
C의 예 :
int dot_product(short *x, short *y, short z)
{
int sum = 0
int i;
assert( ( (int)(x) & 0x3 ) == 0 );
assert( ( (int)(y) & 0x3 ) == 0 );
for( i = 0 ; i < z ; ++i )
sum += x[ i ] * y[ i ];
return sum;
}
이것은 컴파일러에게 배열이 32 비트 경계에 정렬되어 있음을 알려주므로 컴파일러는 해당 정렬에 대한 특정 명령어를 생성 할 수 있습니다.
C ++ 11 N3337 표준 초안
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf
19.3 주장
1 (표 42)에 설명 된 헤더 <cassert>는 C ++ 프로그램 명제를 문서화하기위한 매크로와 명제 검사를 비활성화하는 메커니즘을 제공합니다.
2 내용은 표준 C 라이브러리 헤더 <assert.h>와 동일합니다.
C99 N1256 표준 초안
http://www.open-std.org/JTC1/SC22/WG14/www/docs/n1256.pdf
7.2 진단 <assert.h>
1 헤더
<assert.h>
는 어설 션 매크로를 정의하고로NDEBUG
정의되지 않은 다른 매크로를 나타냅니다<assert.h>
. 경우NDEBUG
<assert.h를> 포함 된 소스 파일의 시점에서 매크로 이름으로 정의되며, 어설 매크로는 단순히 정의#define assert(ignore) ((void)0)
어설 션 매크로
<assert.h>
는 포함될 때마다 NDEBUG의 현재 상태에 따라 재정의 됩니다.2. 주장 매크로는 실제 기능이 아니라 매크로로 구현되어야한다. 실제 함수에 액세스하기 위해 매크로 정의가 억제되면 동작이 정의되지 않습니다.
7.2.1 프로그램 진단
7.2.1.1 주장 매크로
개요
1.
#include <assert.h> void assert(scalar expression);
기술
2 assert 매크로는 진단 테스트를 프로그램에 넣습니다. void 표현식으로 확장됩니다. 실행될 때 (스칼라 유형을 갖는) expression이 false 인 경우 (즉, 0과 비교) 어설 션 매크로는 실패한 특정 호출에 대한 정보 (인수 텍스트, 소스 파일, 소스 라인 번호 및 엔 클로징 함수의 이름 (후자는 각각 사전 처리 매크로
__FILE__
및__LINE__
식별자__func__
) 의 값으로 구현 정의 형식의 표준 오류 스트림에 있습니다. 165) 그런 다음 중단 기능을 호출합니다.보고
3 어설 션 매크로는 값을 반환하지 않습니다.
다른 경우에 assert () 함수를 사용하는 세 가지 주요 이유가 있습니다.
assert () 함수는 주로 디버깅 단계에서 사용되며, 최종 코드에서 방해가 될 수있는 조건을 테스트 할 때마다 printf 문을 사용하여 작성하는 것이 지루합니다.
대규모 소프트웨어 배포에서 assert는 헤더 파일을 assert () 함수에 연결하기 전에 정의 된 NDEBUG 매크로를 사용하여 컴파일러가 assert 문을 무시하도록하는 데 매우 유용합니다.
assert ()는 함수 또는 일부 코드를 디자인 할 때 유용하며 코드가 작동하지 않는 한계에 대한 아이디어를 얻고 기본적으로 가정에 따라 평가하는 if을 포함 시키려고합니다.
평가 한 값이 false 인 경우 프로그램 실행을 중지시키는 기능입니다. 일반적으로 릴리스 설정으로 컴파일 할 때 결과 바이너리로 컴파일되지 않도록 매크로로 둘러싸여 있습니다.
이것은 가정을 테스트하는 데 사용되도록 설계되었습니다. 예를 들면 다음과 같습니다.
void strcpy(char* dest, char* src){
//pointers shouldn't be null
assert(dest!=null);
assert(src!=null);
//copy string
while(*dest++ = *src++);
}
이상적으로는 잘못된 인수로 함수를 호출하는 것과 같이 프로그램에서 오류를 일으킬 수 있고 segfault가 발생하기 전에 assert를 누르거나 예상대로 작동하지 않는 것입니다.
또한이를 사용하여 동적 할당이 성공적인지 확인할 수 있습니다.
코드 예 :
int ** p;
p = new int * [5]; // Dynamic array (size 5) of pointers to int
for (int i = 0; i < 5; ++i) {
p[i] = new int[3]; // Each i(ptr) is now pointing to a dynamic
// array (size 3) of actual int values
}
assert (p); // Check the dynamic allocation.
비슷하다:
if (p == NULL) {
cout << "dynamic allocation failed" << endl;
exit(1);
}
new
지정하지 않은 경우 할당 실패에 대한 예외가 발생합니다 nothrow
. 또한 서식이 이상하고 exit
사악합니다.
assert()
않아야하는 것들을 디버깅하고 스탬핑하기위한 것입니다 .