Comments (8)
Remember you can always go from non const to const. The shared implementation could be the const version. Thank you for the suggestion but you can write good code and still be typesafe.
from cppcoreguidelines.
Andrew, I think you closed this too quickly. Please read this section in Scott Meyer's book -- sorry it was Effective C++, not Effective STL (my mistake) -- (or read the Stack Overflow answers in more detail). You can't just go from a non-const method to a const method:
class A
{
public:
B& getB()
{
// really long code to return access to a B
}
const B& getB() const
{
// QUESTION: How to do I apply DRY principle by calling 'B& getB()' from here?
// There is no way. Trying to do so would be unsafe anyway.
}
const C& getC() const
{
// really long code to return access to a C.
}
C& getC()
{
// QUESTION: How to do I apply DRY principle by calling 'const C& getC() const' from here?
// If I know that the C object the const method returns is actually mutable for a non-const A,
// then I should be able to call the const method and cast away the constness of the result.
return const_cast<C&>(static_cast<const A*>(this)->getC());
}
};
from cppcoreguidelines.
I also agree with @hallsoftware
I devoted a page for a full example here and the exact reference is
Scott Meyers. Effective C++ (3rd edition). ISBN: 0-321-33487-6. Item 3, paragraph 'Avoid duplication in const and non-const member functions'
from cppcoreguidelines.
If templates are an option, the following should be a viable way to practice DRY without const_cast
in many circumstances. I do this myself with some frequency:
class bar;
class foo
{
public:
bar& get_bar() { return get_bar_impl(*this); }
const bar& get_bar() const { return get_bar_impl(*this); }
private:
template< class cv_foo >
static auto get_bar_impl(cv_foo& f) -> decltype(f.get_bar())
{
// Now you have access to a properly cv-qualified foo and
// can get a properly cv-qualified bar reference without
// possibly silently violating type safety by using const_cast
}
};
from cppcoreguidelines.
It looks odd to see this issue open with the 'declined' label. I know the declined label was added when the issue was originally added. Should it be removed now that the issue was reopened?
from cppcoreguidelines.
Discussed 11/30/2015.
@hallsoftware, thanks for the note. @gdr-at-ms will look more thoroughly.
from cppcoreguidelines.
Discussed 21 Dec 2015.
from cppcoreguidelines.
Thanks all, including @john-lynch for the template version (also mentioned on SO).
from cppcoreguidelines.
Related Issues (20)
- F.20 should exclude swap HOT 3
- SF.2 allow inline variables and static inline class member variables HOT 1
- F.16 (pass by reference to const / by value): Request for clarification HOT 6
- Poor (and nearly-incorrect) example for rule F.27 (shared_ptr) HOT 4
- Challenging C.153 "Prefer virtual function to casting" HOT 4
- ES.56 Clarification on moving when assigning to reference outside of scope HOT 3
- F.16 Allow pass-by-value for types that are copied HOT 2
- `gsl::suppress` issues collected: Strings, literals, cases HOT 2
- Hi
- New NL Rule suggestion: Place comment-only lines before the code they apply to HOT 1
- Should/can Expects and Ensures be macros?
- Check for invalidated iterator/dangling reference on heap reallocation HOT 2
- Turning off clang unsafe buffer warnings fails when compiling with a gcc based compiler HOT 2
- CodSoft Internship Task 2 /TASK 2 SIMOPLE CALCULATOR #include <iostream> using namespace std; int main() { double num1, num2; char operation; // Input cout << "Enter first number: "; cin >> num1; cout << "Enter second number: "; cin >> num2; cout << "Enter operation (+, -, *, /): "; cin >> operation; // Calculation and output switch (operation) { case '+': cout << "Result: " << num1 + num2; break; case '-': cout << "Result: " << num1 - num2; break; case '*': cout << "Result: " << num1 * num2; break; case '/': if (num2 != 0) cout << "Result: " << num1 / num2; else cout << "Error! Division by zero."; break; default: cout << "Invalid operation!"; } return 0; } HOT 2
- Cpp programs HOT 3
- C.30: Define a destructor if a class needs an explicit action at object destruction - note HOT 1
- Sss
- Practice HOT 1
- #include HOT 1
- How to refer to the guidelines, bibtex preferred? HOT 2
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from cppcoreguidelines.