문제

헤더 / CPP 파일로 헤더를 선언해야합니까? 분명히 후속 헤더가 요구하는 것들이 더 일찍이어야하고 클래스 특정 헤더는 헤더 범위가 아닌 CPP 범위에 있어야하지만 설정 주문 컨벤션 / 모범 사례가 있습니까?

도움이 되었습니까?

해결책

헤더 파일에는 컴파일 가능하게 만들려면 모든 헤더를 포함해야합니다. 그리고 일부 헤더 대신 포워드 선언을 사용하는 것을 잊지 마십시오.

소스 파일에서 :

  • 해당 헤더 파일
  • 필요한 프로젝트 헤더
  • 제 3 자 라이브러리 헤더
  • 표준 라이브러리 헤더
  • 시스템 헤더

그 순서대로 라이브러리를 자체적으로 포함하는 것을 잊어 버린 헤더 파일을 놓치지 않습니다.

다른 팁

모범 사례 : 모든 .H 파일에는 .H를 포함하는 .CPP가 있어야합니다. 이것은 모든 .h 파일을 먼저 넣을 수 있음을 증명합니다.

헤더에 구현이 필요하지 않더라도 .h 파일을 포함하는 .CPP를 만듭니다.

이것은 당신이 원하는 방식으로 당신의 질문에 대답 할 수 있음을 의미합니다. 어떤 순서를 포함시키는지는 중요하지 않습니다.

추가 팁을 얻으려면이 책을 사용해보십시오. 대규모 C ++ 소프트웨어 설계 - 너무 비싸다는 것은 부끄러운 일이지만 실제로 C ++ 소스 코드 레이아웃을위한 생존 안내서입니다.

헤더 파일에서는 표준 헤더를 먼저 놓은 다음 내 헤더를 넣는 경향이 있습니다 (두 목록은 알파벳순으로 주문됩니다). 구현 파일에서 먼저 헤더에 해당하는 (있는 경우) 표준 헤더 및 기타 종속성 헤더를 넣습니다.

당신이 매크로를 잘 활용하고 #define ; 이 경우 정의 된 매크로가 이전에 포함 된 것을 대체하지 않는지 확인해야합니다 (물론 원하는 경우 제외).

이 진술에 관해

후속 헤더가 요구하는 것은 더 일찍이어야합니다.

헤더는 이전에 포함되는 다른 헤더에 의존해서는 안됩니다! 헤더가 필요한 경우, 여기에는 포함됩니다. 헤더 가드는 여러 가지 포함을 방지합니다.

#ifndef FOO_HEADER_H
#define FOO_HEADER_H
...
#endif

편집하다

이 답변을 썼기 때문에 코드에 포함 지시문을 주문하는 방법을 변경했습니다. 이제 저는 항상 헤더를 표준화 순서로 증가 시키려고 노력하므로 프로젝트의 헤더가 먼저 나오고 제 3 자 라이브러리 헤더가 이어지고 표준 헤더가 뒤 따릅니다.

예를 들어, 내 파일 중 하나가 내가 작성한 라이브러리를 사용하는 경우 QT, Boost 및 표준 라이브러리를 사용하면 다음과 같이 포함됩니다.

//foo.cpp
#include "foo.hpp"

#include <my_library.hpp>
// other headers related to my_library

#include <QtCore/qalgorithms.h>
// other Qt headers

#include <boost/format.hpp> // Boost is arguably more standard than Qt
// other boost headers

#include <algorithms>
// other standard algorithms

내가 그렇게하는 이유는 내 헤더에서 누락 된 종속성을 감지하는 것입니다. my_library.hpp 용도 std::copy, 그러나 포함하지 않습니다 <algorithm>. 내가 그것을 포함한다면 <algorithm> 안에 foo.cpp,이 누락 된 의존성은 눈에 띄지 않습니다. 반대로, 내가 방금 제시 한 순서와 함께, 컴파일러는 std::copy 선언되지 않아 수정할 수 있습니다 my_library.hpp.

각 "라이브러리"그룹에서, 나는 포함 지시서를 알파벳순으로 주문하여 더 쉽게 찾을 수 있도록 노력합니다.

사이드 노트에서는 모범 사례가 헤더 파일 간의 종속성을 최대로 제한하는 것입니다. 파일에는 가능한 한 작은 헤더, 특히 헤더 파일이 포함되어야합니다. 실제로 헤더가 더 많을수록 무언가가 변경되면 더 많은 코드를 다시 컴파일해야합니다. 이러한 종속성을 제한하는 좋은 방법은 전진 선언을 사용하는 것입니다. 전방 선언은 언제 사용할 수 있습니까?).

Google C ++ 스타일 가이드, 이름 및 순서 포함 :

DIR/FOO.CC에서는 DIR2/foo2.h의 물건을 구현하거나 테스트하는 것이 주요 목적으로 다음과 같이 포함됩니다.

  • DIR2/FOO2.H (우선 위치 - 아래 세부 사항 참조).
  • C 시스템 파일.
  • C ++ 시스템 파일.
  • 다른 라이브러리 '.H 파일.
  • 프로젝트의 .H 파일.

나는 그것들을 알파벳 순서로 주문하곤했다 (찾기가 더 쉽다)

"어떻게"는 분명하지 않지만 "무엇"은입니다. 당신의 목표는 당신이 헤더 파일을 포함하는 순서가 중요하지 않도록하는 것입니다 (그리고 나는 결코 "절대!").

도움이되는 도움은 헤더 파일이 CPP 파일을 작성할 때 컴파일하는지 테스트하는 것입니다 (각 헤더 파일마다 하나) 중 하나만 포함합니다.

.CPP 파일의 경우 클래스의 헤더 또는 먼저 구현 한 내용을 포함시켜야 하므로이 헤더가 누락 된 경우를 포함해야합니다. 그런 다음 대부분의 코딩 가이드 라인에는 시스템 헤더, 프로젝트 헤더 두 번째 (예 : Google C ++ 스타일 가이드.

그것은 의존성이며, 그것은 당신이 우리 헤더에 넣은 것에 크게 의존합니다. 사실은 당신이 이것에 대해 정말 악명 높고 포함을 엄격하게 유지하기 위해 최소화 할 수 있다는 것입니다. 그러나 결국 포함 경비원을 사용할 수있는 시나리오에 들어갈 수 있습니다.

#ifndef MY_HEADER_H
#define MY_HEADER_H
//...
#endif

문제는 처음에는 그다지 명백하지는 않지만 소프트웨어의 복잡성이 커짐에 따라 의존성도 커집니다. 당신은 잘 할 수 있고 그것에 대해 똑똑 할 수 있지만 더 큰 C ++ 프로젝트는 일반적으로 포함되어 있습니다. 당신은 시도 할 수 있지만 그렇게 많이 할 수 있습니다. 그러니 부지런하고 당신의 포함에 대해 생각하십시오. 그러나 당신은 어떤 시점에서 주기적 의존성을 가장 확실하게 할 수 있으므로 포함 경비원이 필요한 이유입니다.

헤더에 다른 헤더가 필요한 경우 해당 헤더에 포함됩니다.

포인터 나 참조를 전달하고 가능한 위치를 선언 할 수 있도록 코드를 구조화하십시오.

구현에서는 먼저 정의하는 헤더를 먼저 나열해야합니다 (PCH를 사용하는 경우 Visual Studio를 제외하고 stdafx가 먼저 이동합니다).

나는 일반적으로 필요한대로 나열합니다.

다음 컨벤션이 가장 유용하다는 것을 알았습니다.

모듈 .cpp :

// this is the header used to trigger inclusion of precompiled headers
#include <precompiled.h> 
// this ensures that anything that includes "module.h" works
#include "module.h"
// other headers, usually system headers, the project

중요한 것은 모듈의 헤더를 최초의 비 컴파일 헤더로 배치하는 것입니다. 이것은 "module.h"에 예기치 않은 종속성이 없음을 보장합니다.

느린 디스크 액세스 시간으로 대규모 프로젝트를 진행하고 있다면이 스타일이 빌드 시간을 줄이는 데 사용되는 것을 보았습니다.

모듈 .cpp :

// this is the header used to trigger inclusion of precompiled headers
#include <precompiled.h> 
// this ensures that anything that includes "module.h" works
#include "module.h"
// other headers, usually system headers, the project
#if !defined _OTHER_MODULE_GUARD_
#include "other_module.h"
#endif 

#if !defined _ANOTHER_MODULE_GUARD_
#include "another_module.h"
#endif 

약간의 장점이지만 이미 포함 된 경우 헤더를 검색 / 열지 않기 때문에 디스크를 찾는 데 저장됩니다. 가드 확인이 없으면 컴파일러가 헤더 파일을 찾고 열고 전체 파일을 구문 분석하여 끝납니다. #ifdef전체 파일을 시작합니다.

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