This question already has answers here:
Why use a const member function?
(3 answers)
What are the semantics of a const member function?
(9 answers)
Closed 2 months ago.
This post was edited and submitted for review 2 months ago and failed to reopen the post:
Original close reason(s) were not resolved
Edit: From #Jeremy Friesner's answer, he provides another view point that Why use a const member function & semantics of a const member function don't cover. It can improve clarity and disambiguous your code. People can have a brief idea of what this function is supposed to do or not do at the first glance. Very useful especially in working with others.
I come across the constant function lately.
It says:
Constant functions are those have denied permission when attempting
to change the member variables of their classes.
My questions are
In a programmer perspective, if you don't want a function being able to change member
variables, why not just moving the parts responsible for changing variables outside
of the function at the first place? (e.g using another function)
What/when are some practical moments of having the neediness to use a constant
function?
Appreciate any answers
class Foo
{
public:
int x = 0;
int Bar(int arg) const
{
x++; // fails
return x; // okay
}
};
The purpose of const-tagged methods isn't to prevent the programmer from intentionally modifying member variables, but rather to allow the compiler to assist the programmer by producing a compile-time error when the programmer accidentally modifies a member-variable. This is useful because it's much easier and quicker to correct a compile-time error than to chase down a run-time misbehavior through manual testing.
The const tag also assists later programmers who are reading the class's header file by helping them quickly understand what a method does or does not do. For example, if you see this in a class declaration:
class MyClass
{
[...]
int CalculateTheValue();
... you might ask yourself, "does calling CalculateTheValue() change the state of the MyClass object?" With a name like CalculateTheValue() it seems like it shouldn't, but there's no way to know for sure without finding the corresponding .cpp file and reading through the code that implements that method... which is a tedious and error-prone way to do things.
On the other hand, if you see this:
class MyClass
{
[...]
int CalculateTheValue() const;
... then you know right away that CalculateTheValue() will not modify the MyClass object you call it on, because it says so in the declaration. (if it did try to modify the MyClass object, the code wouldn't compile; so if the code compiled, we know it doesn't modify it)
Related
This question already has answers here:
Method chaining - why is it a good practice, or not?
(19 answers)
Closed 2 years ago.
When is it bad to make the return type of a method its own class? for example:
class Stuff{
public:
Stuff &change_name(std::string name) {...} // is this better,
void change_name(std::sring name) {...} // than this?
};
Is it better to make change_x return Stuff or just make it void? because I don't really see a reason why someone will make a sequence of command when calling the method change_name, or is it may be a good practice to always return a supposed to be void method to return its class?
This pattern is useful if you have a class that is meant to change its state repeatedly. Or more succinct, a class that has its main purpose in changing its state by its client code. As in general, you should try to minimize the number of possible states a class instance can be in, use the return *this technique only when its API is clearly superior compared to void member function return types.
The prototypical example here is a builder-class. When you have a complicated constructor of some class to call, with many parameter that depend on several inputs, it can make sense to wrap the construction into a separate builder class. Example client code:
Builder b{/* ... few arguments */ };
b.setName(/* ... */).
setId(/* ...*).
setSomeNumber(/* ...*).
setSomeState(/* ...*).
setOtherState(/* ...*);
Object thatsWhatIAmInterestedIn = b.construct();
This method chaining is terse compared to the distinct invocation of void member functions, and it will easily be recognized as a builder process.
This question already has answers here:
What is this weird colon-member (" : ") syntax in the constructor?
(14 answers)
Closed 5 years ago.
CWmcaIntf::CWmcaIntf() :
m_hDll(NULL),
m_pLoad(NULL), m_pFree(NULL), m_pSetServer(NULL), m_pSetPort(NULL), m_pIsConnected(NULL),
m_pConnect(NULL), m_pDisconnect(NULL), m_pTransact(NULL), m_pQuery(NULL), m_pRequest(NULL), m_pAttach(NULL),
m_pDetach(NULL), m_pDetachWindow(NULL), m_pDetachAll(NULL), m_pSetOption(NULL),
m_pSetAccountIndexPwd(NULL), m_pSetOrderPwd(NULL), m_pSetHashPwd(NULL), m_pSetAccountNoPwd(NULL), m_pSetAccountNoByIndex(NULL)
i dont know what this grammer means. i am trying to use a header file 'CWamInf'. and want to know different methods or problems .. thanks..
I don't know how much you know about headers classes and stuff so I'll try to explain everything I can.
CWmcaIntf::CWmcaIntf() :
The CWmcaIntf:: means that the function that is about to be defined after the double colon is within the class "CWmcaIntf".
The CWmcaIntf() is a constructor : it has the same name as the class and its purpose is to construct each object of a class depending on the code you put in it. I'd say that often, its only purpose is to initialize member variables. If it isn't clear yet, check this link.
m_hDLL(NULL)
As you most certainly know, programmers tend to respect and harmonize on coding conventions. One of those is to name all member variables by m_something, so your code become easier to understand for you and everyone else.
So here, all you got is a constructor initializing a lot of member variables to NULL, which means that when a CWmcaIntf object will be constructed, its member variables will be equal to nothing and only be modifiable with setters if data are properly encapsulated.
Now if the purpose of your question was for us to tell you more about what does mean the member variables, and what the constructor may do, well don't expect an answer since zero details ae given and nothing even matches the tutorial explaining how to properly ask a question.
In attempting to brush up on my C++, I've been trying to find out the best-practice way of creating accessors.
I want to clarify my understanding and find out if what I'm doing is right. I have several questions, but they seem pretty simple so I've rolled them all into this one Stack Overflow question.
The following is some example code representing what I 'think' is the correct way of doing things:
class MyClass
{
private:
std::string StringMember_;
int IntMember_;
public:
MyClass(const std::string &stringInput, const int &intInput) : StringMember_(stringInput), IntMember_(intInput)
{
}
const std::string &StringMember() const
{
return StringMember_;
}
void StringMember(const std::string &stringInput)
{
StringMember_ = stringInput;
}
const int &IntMember() const
{
return IntMember_;
}
void IntMember(const int &intInput)
{
IntMember_ = intInput;
}
};
My questions are:
Where my accessors return a const reference variable, ie const std::string, this means that it (my class's member variable) cannot be changed. Is that correct?
The last const before a method's body indicates that no members of the class for which that method is a part of can be altered, unless they are designated mutable. Is this also correct?
Where I'm passing in const method parameters, this means that I ensure these parameters are always stored as they were passed in, thus protecting any original variables being passed in from being altered by the method body. Is this also correct?
With regards to the mutable keyword, under what circumstances would I actually want to use this? I've been struggling to think of a good scenario where I'd have a const method that needed to modify class members.
Accessors seem like a good idea, even for data that will never be publicly exposed, because it ensures a single-point of entry, allowing for easier debugging and so on. Am I thinking along the right lines here, or is this in fact totally meaningless, and that there is no need for private accessors?
From a purely syntactical perspective, should I be writing my references like const int& intInput or const int &intInput. Does it really matter where the ampersand is, or is it just a matter of personal preference?
Finally, is what I'm doing in the example above good practice? I plan to start working on a larger personal project, and I want to have these core basics down before I start running into problems later.
I was using this as a reference: https://isocpp.org/wiki/faq/const-correctness
Where my accessors return a const reference variable, ie const std::string, this means that it (my class's member variable) cannot be changed. Is that correct?
Correct. A variable cannot be changed through a const reference.
The last const before a method's body indicates that no members of the class for which that method is a part of can be altered, unless they are designated mutable. Is this also correct?
Correct. It also allows the function to be called on a const object.
Where I'm passing in const method parameters, this means that I ensure these parameters are always stored as they were passed in, thus protecting any original variables being passed in from being altered by the method body. Is this also correct?
Correct. Same can be achieved with accepting the argument by value.
With regards to the mutable keyword, under what circumstances would I actually want to use this?
See When have you used C++ 'mutable' keyword?
Accessors seem like a good idea, even for data that will never be publicly exposed, because it ensures a single-point of entry, allowing for easier debugging and so on. Am I thinking along the right lines here
I don't buy this argument. Watchpoints allow for easy debugging of member variables regardless of where they're accessed from.
From a purely syntactical perspective, should I be writing my references like const int& intInput or const int &intInput.
Both are syntactically equivalent and the choice between them is purely aesthetic.
Finally, is what I'm doing in the example above good practice?
There is no general answer. Accessors are sometimes useful. Often they're redundant. If you provide a function that allows setting the value directly, such as you do here, then you might as well get rid of the accessors and make the member public.
Seems to me like you have a pretty good handle on the concepts here. As far as a mutable example there are lots, here's one: you have a search method, and for performance reasons you cache the last search results... that internal cache would need to be mutable for a const search method. I.e. the external behavior didn't change, but internally something might change.
Here is some examples for mutable:
memoiziation caches, for when something is referencially-transparent,
but expensive to calculate, the first call to the (const-qualified)
accessor calculates the value and stores it in a mutable member hash
table, second and subsequent calls fetch the value from the table
instead.
access counters, timing, loggers, and other instrumentation that needs
to change some state when a const-qualified accessor is called
From https://www.quora.com/When-should-I-actually-use-a-mutable-keyword-in-C++
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 9 years ago.
Improve this question
What's the difference between the following 4 styles of calling another member function?
Is there a benefit that causes that one method is preferrable?
void Object::trigger() {
(*this).triggerinner(10);
this->triggerinner(10);
triggerinner(10);
Object::triggerinner(10);
}
void Object::triggerinner(int x) {
std::cout << "trigger" << std::endl;
}
The first three are fundamentally the same in non-template code.
In a template member function, the first two make the name
lookup dependent (so the compiler can find names in a dependent
base class). Generally, simpler is better, so most people favor
the third form, except when the dependend lookup is necessary,
in which case they will use the second.
The fourth form blocks virtual resolution. (And it has, in
fact, the same three forms as above, i.e.
this->Object::triggerinner(10), etc.) You use it when you
want to force the resolution: the function called will be in
Object or in a base class of Object, but never in a derived
class, even if the function is virtual. This is most often used
in a derived class, to call the base class implementation before
(or after) doing additional work:
void
Derived::func()
{
Base::func();
// Additional work here...
}
Outside of a member function, it can also be used to call
a static member function when you don't have an object.
The first two are exactly equivalent to each other. By definition, (*p).thing and p->thing are equivalent for any pointer.
The third is equivalent in this situation; but could have a different meaning if the member function's name were hidden by a local declaration. There are also situations (where the function is a member of a base class, and templates are involved) when this form won't find the function, in which case you would have to use one of the others.
The fourth is equivalent if the function is not virtual. If it is virtual, then this will force a non-virtual call to the override available in this class, rather than the final override.
(*this).triggerinner(10);
It's ugly, "->" is there to avoid to do that.
this->triggerinner(10);
It's fine but this-> is not mandatory. If you are working on an existing project, keep the current coding style.
triggerinner(10);
It's fine, same comment than the solution using this->.
Object::triggerinner(10);
Use this for static methods.
I would suggest you to use triggerinner(10) since it's short and clear.
the most frequently used one is this->triggerinner(10);.The reason it makes an easy match using the pointer with table.
this->triggerinner(10) is better than the others:
Better than (*this).triggerinner(10) because it is more readable.
better than triggerinner(10), because in this case you will not know if triggerinner() is a method or a function (with a different scope then).
Better than Object::triggerinner(10) which is mainly used for static methods (but not only)
There is no difference, unless your compiler does some funky stuff. Try reading the assembly language generated by the lines in your function and see if there are any differences or if its the same block of instructions generated over and over.
As for the "best" or " most popular" one that comes down to your personal preference or when working at a company they might enforce certain coding standards forcing you to write in a specific way when doing something every time.
I have a class A.Now this has a method say performSomething(). This essentially takes a LINE as input and checks what type of LINE it is and branches accordingly and perform the intended task;
Class A
{
performSomething( LINE )
{
check LINE TYPE
switch( LINE ) {
}
}
};
Now, Im being asked to introduce a new inner class to do this operation in it. Now, here comes the trouble. Im not at all sure what he means by that or if that actually makes any sense here!.
Thing is I NEED LINE(input parameter) if I need to proceed further. But if I chose to design the new class as a LOCAL class(class inside method), then I can't access it[as local auto variable are not accessible];[i posted a question on this too).
I neither feel that this can be addressed by using NESTED class(class inside class);But Im, not quite sure about it.
He also insists that the LINE will be available in the nested class and so I need not worry about it. But what's breaking my head is that this line is not an instance variable. It is jus t an AUtomatic variable.
So, please someone point me out if this can be achieved thorough nested classes.
Thanks,
Moanr Pavan.
Well, there's quite a bit wrong with the code so far.
For instance, the switch is very likely the wrong approach to polymorphism. In C++ we generally use virtual functions for that, but sometimes we can also use function overloading and/or templates (if the actual types are already known at compile time).
Secondly, there's no rationale stated for an "inner" class, nor is it clear what that means. You can have classes inside other classes, and even classes inside functions. So the following would be syntactically OK:
class A
{
void performSomething( LINE )
{
class B {
static void performSomething(A* that, LINE) { code };
};
B::performSomething(this, LINE);
}
};
Your compiler will accept this, but we have to ask: what's the point of this? Also, note that B::performSomething can only access the members from A if we explicitly pass this.