[C] 왜 일부 커널 프로그래머는 간단한 while 루프 대신 goto를 사용합니까?


Answers

이 예제의 경우, 원래 SMP가 아닌 방식으로 작성된 코드에 SMP 지원을 추가하는 것이 었습니다. goto again; 추가하기 goto again; 경로는 기능을 재구성하는 것보다 훨씬 간단하고 덜 침해 적입니다.

나는이 스타일을 많이 좋아한다고 말할 수는 없지만, 나는 또한 이데올로기 적 이유로 goto 를 피하는 것이 잘못되었다고 생각한다. goto 사용법의 특별한 경우 (이 예제와 다른 경우)는 goto 가 함수에서 앞으로 이동하는 데에만 사용되며 goto 사용되지 않습니다. 이 클래스의 사용법은 결코 goto 에서 발생하는 루프 구조를 생성하지 않으며 거의 ​​항상 필요한 동작을 구현하는 가장 단순하고 명확한 방법입니다 (일반적으로 오류를 정리하고 오류로 돌아 오는 경우).

Question

제가 C를 배웠을 때, 선생님은 하루 종일 저에게 말했습니다. "고토를 사용하지 마십시오. 나쁜 습관, 추한 것, 위험합니다!" 등등.

그렇다면 왜 일부 커널 프로그래머는 goto 사용합니까? 예 goto 함수 에서는 간단한 것으로 대체 할 수 있습니다.

while(condition) {} 

또는

do {} while(condition);

나는 그것을 이해할 수 없다. while / do 대신에 goto를 사용하는 것이 더 나은 경우가 있습니까? 그렇다면 왜?




역사적 맥락 : Dijkstra는 1968 년에 많은 프로그래머가 goto구조화 된 프로그래밍 ( if , while , for 등) 대신 사용하여 Goto Considered Harmful 을 작성했음을 기억해야합니다.

44 년이 지난 지금 야생에서 goto 를 사용하는 것은 드문 일입니다. 오래 전에 이미 구조화 된 프로그래밍이 이루어졌습니다.

사례 분석 :

예제 코드는 다음과 같습니다.

    SETUP...
again:
    COMPUTE SOME VALUES...
    if (cmpxchg64(ptr, old_val, val) != old_val)
        goto again;

구조화 된 버전은 다음과 같습니다.

SETUP...
do {
    COMPUTE SOME VALUES...
} while (cmpxchg64(ptr, old_val, val) != old_val);

구조화 된 버전을 보면 즉시 "루프"라고 생각합니다. 내가 goto 버전을 볼 때, 나는 그것을 "try again"case가있는 직선으로 생각한다.

goto 버전에는 동일한 열에 SETUPCOMPUTE SOME VALUES 가 모두 있습니다. 대부분의 경우 제어 흐름이 둘 다 통과한다는 점을 강조합니다. 구조화 된 버전은 다른 열에 SETUPCOMPUTE SOME VALUES 를 두었습니다. 제어가이를 통해 다르게 통과 할 수 있음을 강조합니다.

여기서 질문은 코드에 어떤 유형의 강조를 넣고 싶습니까? 이것을 오류 처리를 위해 goto 와 비교할 수 있습니다 :

구조화 된 버전 :

if (do_something() != ERR) {
    if (do_something2() != ERR) {
        if (do_something3() != ERR) {
            if (do_something4() != ERR) {
                ...

고토 버전 :

if (do_something() == ERR)  // Straight line
    goto error;             // |
if (do_something2() == ERR) // |
    goto error;             // |
if (do_something3() == ERR) // |
    goto error;             // V
if (do_something4() == ERR) // emphasizes normal control flow
    goto error;

생성 된 코드는 기본적으로 동일하므로 들여 쓰기와 같은 인쇄상의 우려라고 생각할 수 있습니다.