5
Google C++ Style Guide
based on https://google.github.io/styleguide/cppguide.html
mmass_sern
ยทOct 20, 2025ยท40 views# Google C++ Style Guide
Based on https://google.github.io/styleguide/cppguide.html
## C++ Version
Target C++20. No C++23. No non-standard extensions.
## Headers
Self-contained. End in `.h`. Include what you use.
Guard format: `<PROJECT>_<PATH>_<FILE>_H_`
```cpp
#ifndef FOO_BAR_BAZ_H_
#define FOO_BAR_BAZ_H_
...
#endif // FOO_BAR_BAZ_H_
```
Include order:
1. Related header
2. C system headers (angle brackets, `.h` extension)
3. C++ standard library (no extension)
4. Other libraries
5. Project headers
Blank line between groups. Alphabetical within.
No forward declarations. Include the header.
Short inline functions OK in headers (~10 lines). Longer ones go in `.cc`.
## Scoping
Use namespaces. Never `using namespace`. Never declare in `std`.
Terminate with `} // namespace foo`.
Unnamed namespace or `static` for file-local stuff. Never in headers.
Declare variables in narrowest scope. Initialize at declaration.
```cpp
while (const char* p = strchr(str, '/')) str = p + 1;
```
Static/global: trivially destructible only. Use `constexpr` or `constinit`.
`thread_local` at class/namespace scope: must be `constinit`.
## Classes
Data members `private`. Always. Trailing underscore: `member_`.
Structs: passive data only, all public, no trailing underscore.
Explicitly declare or `= delete` copy/move ops.
```cpp
class Copyable {
public:
Copyable(const Copyable&) = default;
Copyable& operator=(const Copyable&) = default;
};
class MoveOnly {
public:
MoveOnly(MoveOnly&&) = default;
MoveOnly& operator=(MoveOnly&&) = default;
MoveOnly(const MoveOnly&) = delete;
MoveOnly& operator=(const MoveOnly&) = delete;
};
```
Prefer composition over inheritance. `public` inheritance only.
Use `override` or `final`. Never `virtual` on overrides.
No virtual calls in constructors. No failing init in constructors.
Mark single-arg constructors `explicit`. Mark conversion operators `explicit`.
Declaration order: `public`, then `protected`, then `private`. 1-space indent for access specifiers.
Within each section:
1. Types and aliases
2. Static constants
3. Factory functions
4. Constructors/assignment
5. Destructor
6. Methods
7. Data members
## Functions
Return values, not output parameters. Return by value or reference, not raw pointer unless nullable.
Input params: values or `const&`. Output params: references (non-null) or pointers (nullable).
Keep functions short. ~40 lines max.
Overload only when semantics identical.
Default args: non-virtual only, constants only.
Use trailing return type only when required (lambdas, complex templates).
## Ownership
`std::unique_ptr` for ownership transfer.
`std::shared_ptr` only when actually shared. Prefer `shared_ptr<const Foo>`.
Never `std::auto_ptr`.
## Other C++ Features
Rvalue refs: only for move ops, `&&`-qualified methods, perfect forwarding.
Friends: OK within reason. Define in same file.
No exceptions.
`noexcept`: use when useful for performance. Unconditional if exceptions disabled.
No RTTI except tests. No `typeid`, no `dynamic_cast` decision trees.
No C-style casts. Use `static_cast`, `const_cast`, `reinterpret_cast`, `std::bit_cast`.
Prefer `++i` over `i++`.
Use `const` on APIs. Methods: `const` unless they mutate state.
`constexpr` for true constants. Don't overcomplicate to enable it.
Integer types: use `int` for small values. Use `<stdint.h>` types (`int64_t`, etc.) for specific sizes. Avoid unsigned except for bit patterns.
No `long double`. Use `float` and `double` only.
Avoid macros. If needed: `ALL_CAPS`, project prefix, `#undef` after use.
`nullptr` for pointers. `'\0'` for null char.
`sizeof(varname)` over `sizeof(type)`.
`auto`: use only when it makes code clearer. Not to avoid typing.
No CTAD unless template opts in with explicit deduction guides.
Lambdas: prefer explicit captures. `[&]` only for short-lived lambdas. No `[=]` with `this`.
```cpp
[&foo] { Frobnicate(foo); } // Good - explicit
[&] { Frobnicate(foo); } // Bad if lambda escapes
```
No template metaprogramming abuse. Keep it simple.
Use `requires(Concept<T>)` syntax over `template<Concept T>`.
No C++20 modules. No coroutines except approved libraries.
Boost: only approved subset (call_traits, compressed_pair, graph, iterator, polygon/voronoi, bimap, math, multi_index, heap, flat containers, intrusive, sort, preprocessor).
No `<ratio>`, `<cfenv>`, `<filesystem>`.
Switch: always `default` case. Use `[[fallthrough]]` for fall-through.
## Naming
Descriptive. Proportional to scope. Minimize abbreviations.
```
ClassName PascalCase
ConceptName PascalCase
FunctionName PascalCase
variable_name snake_case
class_member_ snake_case with trailing _
struct_member snake_case, no trailing _
kConstantName k + PascalCase
MACRO_NAME ALL_CAPS
namespace_name snake_case
kEnumValue k + PascalCase (not ENUM_VALUE)
```
File names: lowercase, `_` or `-`. Use `.cc` and `.h`.
Accessors/mutators may be snake_case: `int count()`, `void set_count(int)`.
## Comments
`//` preferred. Be consistent.
File: license boilerplate, then optional overview.
Class: what it's for, how to use it, thread safety.
Function declaration: what it does, not how. Document ownership, nullability, side effects.
Function definition: tricky implementation details.
Variables: clarify sentinel values, non-obvious usage.
TODO format:
```cpp
// TODO: bug 12345678 - Remove after Q4 2025.
// TODO(username): Fix this.
```
## Format
80 char line limit. Exceptions: URLs, include paths, guard macros.
2-space indent. No tabs.
```cpp
ReturnType ClassName::FunctionName(Type par1, Type par2) {
DoSomething();
}
// Long params
ReturnType LongClassName::ReallyLongFunctionName(
Type par1, // 4 space indent
Type par2,
Type par3) {
DoSomething(); // 2 space indent
}
```
Braces on same line. Always use braces for loops/conditionals (exception: single-line OK).
```cpp
if (condition) {
DoThing();
} else {
DoOther();
}
if (x == kFoo) return new Foo(); // OK - single line
```
No spaces inside parens. Space after `if`, `for`, `while`, `switch`.
Pointer/reference: `char* c`, not `char *c`. No space before `*` or `&`.
Namespace contents not indented.
```cpp
namespace foo {
void Bar();
} // namespace foo
```
Class format:
```cpp
class MyClass : public Base {
public: // 1 space indent
MyClass(); // 2 space indent
private:
int member_;
};
```
Constructor init lists:
```cpp
MyClass::MyClass(int var)
: member_(var),
other_(var + 1) {
DoSomething();
}
```
Lambda:
```cpp
auto fn = [&x](int n) -> int { return x + n; };
```
Preincrement: `++i`, not `i++`.
Vertical whitespace: sparingly. No blank lines at start/end of blocks.
Full guide: https://google.github.io/styleguide/cppguide.html
Comments
No comments yet
Be the first to share your thoughts!