To explain why a method would be better, I will start by explaining the differences between a method and a function from a programmer's perspective.
1.) Functions are defined in the global namespace and not in a class. As long as they are not marked static, they can be accessed from any file as long that file is made aware of them. Functions only have access to the arguments you pass into their parameters, and then possibly global, static, or local variables in their lexical scope. They CANNOT access objects or data that is defined within the scope of another function or a scope that is inaccessible to them without being explicitly passed that data as a parameter (a scope is the region between the function's curly braces: {.....} ).
2.) Methods are almost like functions, except for a few things. First, they are defined within the scope of a class. Many beginners believe that is where the differences end and methods can be used as a normal function is used. They falsely believe that a method of a class is basically a global function within the class. But there is an important difference.
Whenever you call a method in C++, you pass a hidden parameter that is not part of the explicitly stated parameters. This hidden parameter is a pointer to the class object that called it, and it is called
this
. When you dereference the
this
pointer, you will receive the object that called the method in the first place. For example, the
this
pointer of the method
foo
will contain the address of the
MyObject
instance and thus it will be able to access its data members. Note that
this
is passed implicitly even though
foo
is a nullary method (has no explicit parameters).
MyObject.foo()
Whenever a data member, lets say
d1
is accessed inside the scope of
foo
, the data member accessed is of the object pointed to by the
this
pointer. You could also explicitly access the
d1
data member by using
this->d1
, but it is not necessary unless using it for disambiguation purposes because the compiler will do this for you in methods automatically when simply referring to
d1
.
Now, coming back to your question. Why should
getInfo()
be a method rather than a simple function? See the difference between this code and you will see:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55
|
#include <iostream>
class Personal
{
public:
void getInfo();
int getVar() {return TestVar;}
private:
const int TestVar = 7;
};
void Personal::getInfo()
{
//Code can access the data members directly, without using "setters" because of the "this" pointer:
std::cout << "Method: TestVar is " << TestVar << "\n";
//This is the same thing as:
std::cout << "Method: TestVar is also " << this->TestVar << "\n";
}
void getInfo(Personal& my_info)
{
//Code accesses through setter methods and getter methods of my_info
std::cout << "Function: TestVar is " << my_info.getVar() << "\n";
//There is no "this" pointer, so cannot access private member TestVar directly!
//std::cout << "Function: TestVar is " << this->TestVar << "\n"; //ERROR!
}
int main()
{
Personal James_Doe;
//Which syntax do you think is cleaner and makes more sense for Mr. Doe?
//This?
James_Doe.getInfo();
//Or This?
getInfo(James_Doe);
//Having getInfo as a method of the class makes more sense because you are accessing Mr. James Doe's information, which is stored in the class.
//This is much cleaner than having a function outside of the class take a reference to a Method::Personal object when the method itself stores
//the object in a "this" pointer. Plus, you can access the data members directly without having to use setter methods. Cleaner implementation.
//
//Summary of why it should be a method:
// Syntactical Advantage:
// * Accessing it is cleaner, you are accessing the getInfo method of James Doe's personal record, which should be located in the class
// * No need to pass in the object
// * Can access private data members implicitly using the "this" pointer without setters and getters.
// * If getInfo() is a method, you can get rid of all the setter methods and use this method exclusively.
// You will reduce the size of your class because there would be no need to change a record outside of
// this method (unless you need the setters for some reason)
// Logical Advantage:
// * It makes more sense to be able to "get info" from within James Doe's class rather than outside of it.
|
Also, you should think of objects of a class as individual, seperate instances. You use "Personal info" which creates a single instance named "info." A better way to think of it is that every object of class Personal is the record of a person, such as John Doe. Each object can thus be a single record of a person in your Personal Information database.