2012-02-13 2 views
1

상태 (예 : 통과/실패)가 변경 될 때마다 메시지를 한 번만 기록해야하므로 (로그를 복잡하게 만들지 않아도 됨) do-while 루프가 있습니다. 루프를 통과 할 때마다 다른 일을 할 수 있습니다. 간단한 부울 변수를 사용하면 기본적으로 메시지를 이미 기록했는지 알 수 있습니다.이 메시지는 알려진 상태에있는 경우 작동합니다. 그러나 두 경우 모두 처음으로 메시지를 인쇄하려면 (통과/실패) 해당 계정을 고려해야합니다. 예를 들어, 조건을 true으로 기본 설정하고 처음으로 사실 인 경우 참인 것으로 '참'하다는 메시지를 기록하지 않습니다 (그 반대의 경우는 false).).do-while을 통한 첫 번째 패스 감지

이것은 i.c. = Null로 부울을 넣을 때 좋은 장소 인 것처럼 보입니다. 그러나 이들이 존재하지 않는 언어에서는 무엇을해야할까요?

내가 생각할 수있는 가장 간단한 해결책은 'firstTime = True'와 같은 부가적인 부울 변수를 사용하는 것이지만, 그것을 사용하면보다 민감한 방법으로 기본 감정을 해결해야한다고 생각할 때 항상 나를 괴롭힌다. . 또 다른 옵션은 do-while의 브레이크 아웃 조건을 조건으로 사용하는 변수의 초기 조건으로 사용하는 것이지만 누군가가 int status = STATUS_QUIT을 읽을 때 혼란 스러우며 확실히 bool firstTime = true보다 자세한 설명이 필요합니다. 세 번째 옵션은 bool 대신 enum을 사용하고 {firstTime, true, false} 또는 다른 것이 있습니다.

다른 하나를 사용하는 다른 이유가 있습니까, 아니면 더 좋은 방법이 있습니까?

내가 생각 해낸 두 가지 옵션

코드 예제 :

bool firsttime 사용 :

bool firstTime = true, infoFound = false; 
do 
{ 
    if (getInfo()) 
    { 
     if (!infoFound) 
     { 
      // log it (ONCE)(important) 
      infoFound = true; 
     } 
     // use info (every time) 
    } 
    else if (infoFound || firstTime) 
    { 
     // log it (ONCE)(important) 
     infoFound = false; 
     firstTime = false; 
    } 
// FYI, WaitForStatusUpdate is a blocking call... 
} while (STATUS_QUIT != WaitForStatusUpdate()); 

사용 체크 변수에 대한 초기 조건으로 while 루프 '브레이크 아웃 상태'
(status은 do-while의 끝에서 업데이트되므로 do 섹션은 다시 실행되지 않습니다. status == breakOutCondition; 우리 우리의 이점을 여기에 사용하고 status = breakOutContition 초기 설정 - 그것을 통해 처음으로 breakOutCondition되지만 모든 후속 루프 될 것입니다 뭔가 다른 ... 그것은 해킹의 일종으로 아직도 확실하지 않다 .. .

bool infoFound = false; 
int status = STATUS_QUIT; 
do 
{ 
    if (getInfo()) 
    { 
     if (!infoFound) 
     { 
      // log it (ONCE)(important) 
      infoFound = true; 
     } 
     // use info (every time) 
    } 
    else if (infoFound || firstTime) 
    { 
     // log it (ONCE)(important) 
     infoFound = false; 
    } 
    status = WaitForStatusUpdate(); 
} while (STATUS_QUIT != status); 

(내가 사용하고있어 그 이후 C++로이 태그를 해요,하지만 정말 비슷한 구조를 가진 모든 언어에 적용 할 수있는)

+1

C++을 사용하는 경우 'BOOL'및 'TRUE/FALSE'대신 'bool' 및'true/false'를 사용해야합니다. –

+0

@ DavidRodríguez-dribeas : 예, 우리는 위풍 당당하고 있습니다.h는'#define FALSE 0'을 가지고 있지만, 다른 사람들이 컴파일하지 않고 컴파일 할 수 있도록 여기에서'false'로 바꿀 것입니다 ... good catch :) – johnny

+0

이상하게도 (또는 아마도?), 그것은 windef로 보입니다 'BOOL'을'int'로 정의했기 때문에 정수 (또는 열거 형)를 사용하여 같은 결과를 얻을 수있었습니다 ... 그러나 다시,이 질문에 대한 windows 관련 문제를 멀리두고 싶습니다. 일반적으로 C와의 호환성을 위해 – johnny

답변

2

열거 형이 명확하지 않습니까?

enum State { Unknown, Pass, Fail }; 
State state = Unknown; 
... 
State newState = getInfo() ? Pass : Fail; 
if (newState != state) { log(); state = newState; } 
+1

이것은 나의 원래 생각 중 하나였습니다 (OP에서 언급 된 '세 번째 옵션'). 아마도 가장 깨끗한 것 일지 모르지만 과잉 공격이 될 가능성이 있다고 생각하십니까? 어쨌든, 나는 다른 사람들이 생각한 것을보고 관심을 보였다. – johnny

+0

열거 형을 사용하는 데 부분적으로 끔찍하지 않은 이유 중 하나는 다음과 같은 조건을 사용하지 않고 상태를 확인하는 좋은 방법을 생각할 수 없다는 것입니다. 'if (info bound state)'와는 달리'if ((infoFound == state) || (newState == state))'('State state'와 함께)'- 하지만 이것은 선호도의 문제로 어쨌든 종기가 될 수도 있습니다 ... – johnny

+0

글쎄, 내게 이것은 알고리즘의 명확한 표현입니다; 나는 두 플래그로 혼란스러워. 그러나 그것은 실제로 단지 맛의 문제일지도 모릅니다. –

1

C++ 거의 널 (NULL) 논리 값을 가지고, boost::optional<bool>는 할 것 트릭 나는 믿습니다.

C++에서이를 수행하는 일반적인 방법 중 하나는 적절한 컨텍스트에서 작성하는 스트림 래퍼이며 플러시 된 횟수와 반복적으로 발생하는 로깅을 방지합니다. 로깅을 정상적으로 수행하고 스트림이 랩핑 된 스트림으로 보낼지 여부를 결정하도록합니다.

+0

스트림 래퍼 아이디어에 감사드립니다. 더 자세히 살펴 봐야 할 것입니다. 확실히 그것보다 더 많은 작업이 될 것입니다. 이 응용 프로그램에 대한 가치는 있지만 일반적으로 좋은 구현이 될 수 있습니다 ... – johnny

+0

부스트를 사용하는 경우 ['boost :: logic :: tribool'] (http://www.boost.org/doc/libs/release/doc /html/boost/logic/tribool.html)이 더 편리 할 수 ​​있습니다. –

관련 문제