Reference:
[Book] https://www.amazon.com/Beautiful-Core-Guidelines-Writing-Clean/dp/0137647840
[Cpp core guideline] https://isocpp.github.io/CppCoreGuidelines/CppCoreGuidelines#main
F.51: Where there is a choice, prefer default arguments over overloading
C.45: Don’t define a default constructor that only initializes data members; use in-class member initializers instead
C.131: Avoid trivial getters and setters
ES.10: Declare one name (only) per declaration
NR.2: Don’t insist to have only a single return-statement in a function
P.11: Encapsulate messy constructs, rather than spreading through the code
I.23: Keep the number of function arguments low
Do as little as possible, but no less
x64 ABI, there is a four-register fast-call calling convention by default.
A four-parameter function will execute slightly faster than a function taking a class by reference.
I.26: If you want a cross-compiler ABI, use a C-style subset
C.47: Define and initialize member variables in the order of member declaration
CP.3: Minimize explicit sharing of writable data
CP.22: Never call unknown code while holding a lock (e.g., a callback)
"Don’t communicate by sharing memory; share memory by communicating"
T.120: Use template metaprogramming only when you really need to
Meta-programming techniques, while useful, have been adopted into the lan- guage more explicitly.
consider using concept in C++20.
I.11: Never transfer ownership by a raw pointer (T*) or reference (T&)
Your default choice for holding objects with dynamic storage duration should be a std::unique_ ptr.
You should only use std::shared_ptr where reasoning about lifetime and ownership is impossibly hard, and even then, you should treat it as a sign of impending technical debt caused by a failure to observe the appropriate abstraction.
Use GSL:
http://github.com/Microsoft/GSL
I.3: Avoid singletons
C.90: Rely on constructors and assignment operators, not memset and memcpy
ES.50: Don’t cast away const
ES.5: Keep scopes small
CP.43: Minimize time spent in a critical section
E.28: Avoid error handling based on global state (e.g. errno)
You do not know how your calling code is going to respond to errors.
You cannot rely on your caller handling the error.
SF.7: Don’t write using namespace at global scope in a "header file"
F.21: To return multiple “out” values, prefer returning a struct or tuple
Enum.3: Prefer class enums over “plain” enums
ES.5: Keep scopes small
only declare auto-variables that is close to its use. (Golang)
Con.5: Use constexpr for values that can be computed at compile time
T.1: Use templates to raise the level of abstraction of code
T.10: Specify concepts for all template arguments (C++20)
P.4: Ideally, a program should be statically type safe
Problem areas:
- unions - use variant (in C++17)
- casts - minimize their use; templates can help
- array decay - use span (from the GSL)
- range errors - use span
- narrowing conversions - minimize their use and use narrow or narrow_cast (from the GSL) where they are necessary
P.10: Prefer immutable data to mutable data
I.30: Encapsulate rule violations
ES.22: Don’t declare a variable until you have a value to initialize it with
Declaring at point of use improves readability of code, and not declaring state at all improves things even further. Reasoning about state requires a comprehensive memory, which is a diminishing asset as codebases expand.
Per.7: Design to enable optimization
E.6: Use RAII to prevent leaks
No comments:
Post a Comment
Note: Only a member of this blog may post a comment.