getters and setters vs public vars

This question isn’t related to any particular problem, but more to see the opinions on encapsulation for games.

I know that the idea is to make classes in such a way that code can be reused as simply as possible…

It makes sense when you are dealing with buttons, or tangible objects… however, when you are dealing with objects that are more or less abstract, like a collisionhandler, input handler, etc… and other things that will depend on the structure of the game and not necessarily be reusable elsewhere, is there any reason why it would be better to use “player.getSpeed()” then “player.setSpeed()” vs “player.speed = x”…

So, is there any other reason that I’m missing as to why I should use getters and setters over direct access?

The reason for using getters and setters instead of making your members public is that it makes it possible to change the implementation without changing the interface.
Also, many tools and toolkits that use reflection to examine objects only accept objects that have getters and setters. JavaBeans for example must have getters and setters as well as some other requirements.
Also, the fields of a class can be made read-only or write-only.

a variable like “speed” in your example would be good (in my opinion) to make public. This is because you cant do:
player.speed++;
player.speed *= 10;
player.speed %= 30;
etc…
easily with getters and setters

Actually, its probably to do with poor planning and execution (being a noob, mostly), but I find myself writing functions where I would want to have multiple return statements…

Like in the collision handler, I would want to return the player position after resolving the collision, the start and end points of the line that was collided, and changing the player speed (from falling to not falling) just as an example, and find it easier to just use class variables directly over get and set… I am quite certain there’s no way to return multiple variables of different types.

I was mostly just asking to see if there wasn’t any consequences to my laziness beyond that the code would not be easily reusable… I’ll wait to see if there are other issues, but you both bring up good points about why it is worth the effort and hassle to use the get and set methods where possible.

You can either pass an object as a parameter and edit it, or return a new instance of a class.
SOLID may also help with a reusable design for your game.

Encapsulation. A class of objects should manage its own state.

If you’ve got code all over the place directly manipulating the speed of the player (either the member directly, or through getters/setters), then you’ve failed to properly encapsulate your code.

Encapsulation and proper dependency management are crucial for writing maintainable software.
What may look today like a valid and convenient shortcut will evolve into an uncontrollable monster over the time. Starting with a bad practice is like injecting a virus into a software system. The next time you will remember it and say, alright, wasn’t that bad, it works, I know how things work, only once again. Not to speak of programming with several people.
Even only developing one year on a game is more than enough to leave a mess behind.
Bad, bad practice.

Assuming the code is only being used in it’s own project, and you get tired of your public variables, then all you have to do is change the public variable to private and fix the broken references. It’s no big deal.

If your code is shared across several projects or by several people, then you have an insoluble mess with public non-final mutable variables.

short answer:
If you use Var – in 3-5 places – Use public

For else create get/set
“getters / setters” - var changes, can be easily searched (separate) by IDE,
and can help resolve many problems + it can be overwrite

getters and setters vs public vars
But you don’t need create get/set for every variable (even if its right style)
Because as result you receive tons of code, that you don’t really need

Less code sometimes better than right pattern style :wink:

up:

or even
(if you use Fun in one Thread)


public void Proc_Collis(){
	Return_Collis.Reset_Data();
	...
	Return_Collis.have_Collis = true;
	...
}
class Return_Collis{
	static public have_Collis;
	....
	static public void Reset_Data(){
		have_Collis = false;
		...
	}
}

Wow, I would never be calm again :expressionless:
-ClaasJG

This makes sense, and gives a different approach to code, IMO at least…
Sounds like its better to start vague and work towards the code to make it work…

ex: start with an entity that has a position and size, and from that is a character that extends an entity, and can move, jump, attack and then either gets extended to an enemy or player which implements…

That’s why I was asking, because it’s only me, so I was thinking “why should I stress myself out over the grief caused by get/set methods”, and you all have offered some very good reasons why its bad form.

Every [icode]…[/icode] have sense ^^


public void Proc_Collis(){
	Return_Collis.Reset_Data();//Always first
	if(!Check_Colis()){
		return;
	}
	Return_Collis.have_Collis = true;
	///calculate Pos_Offset + Velocity
}
class Return_Collis{
   static public boolean have_Collis;
   static public Vec3 Velocity;
   static public Vec3 Pos_Offset;

   static public void Reset_Data(){
      have_Collis = false;
      Velocity = new Vec3();
      Pos_Offset = new Vec3();
   }
}

If I encountered that in a code base, I’d run for the hills.

It can be replaced for instance of class with local variables :wink:


public Return_Collis Proc_Collis(){
	Return_Collis ret_Obj = new Return_Collis();// Reset_Data(); in Constructor
	if(!Check_Colis()){
		return ret_Obj;
	}
	ret_Obj.have_Collis = true;
	///calculate Pos_Offset + Velocity
}

In my opinion, pretty much what Abuse is saying here is right. Or, at least, it is what I practice. Truly you shouldn’t be modifying class variables from tons and tons of other classes, it should all be managed and maintained in its own class so that it can be retrieved for use in other classes. As a result, unless I am in a hurry and/or don’t care about how good my code is (E.g. when I switch from programming in my 3D Game Library to programming in my 3D Game Library test/debug program), I almost always use getters/setters. I’ve just been taught that doing so was best practice.

I’m browsing through the classes of my 3D Game Library and I can’t seem to find any public vars in my code, they all use getters/setters. But then again I am programming using a Component Based Architecture. Another reason for using getters/setters is that it gives you control over mutability.

I dunno why I read [icode]vars[/icode] as [icode]wars[/icode] in the title at first, but here are my opinions in that regard. Note that I have changed my style, after coming to know of the 64k method limit on android, but I like this new style, as this is more simple.

Rule #1: Prefer to use public variables when they make sense

For example, take a class which is only a container of data, such as a [icode]Vector2[/icode]. Then it is better to leave the variables x and y as public. Using setters and getters is not a good option because it’s not clean.


// Clean way, using public variables.
speed.x += 4;

// Not so clean when you use getters and setters
speed.setX(speed.getX() + 4);

Using getters and setters like this will make your code look complex. However do this only when you need no validation on the variables, like in this case. It is a simple data class so keep them as public.

Rule #2: For objects that don’t need to be set, consider using [icode]final[/icode] and public.

For example, you have to write a class that has a property called position, and it is of type [icode]Vector2[/icode]. Now you want your users to be setting its contents and not itself directly. Use the final keyword here, and initialize it once in the constructor.


// This works, and you intend to do this simply.
entity.position.x += 4;

// But this will give an error if you try to assign it.
@@entity.position = new Vector2();

// And you just do this in the class, pretty simple.
public final Vector2 position = new Vector2();

This gives a benefit that you do not need to evaluate the variable each time for being null, and we can enjoy the simplicity too. Keep in mind that getters and setters are needed if the data requires validation.

Rule #3: Use Getters in case you need the value to be readonly to users and not in that same class.

Yes, in case you are needed to set the value of the variable internally and prevent the user from accessing it, use a getter and make it private or protected. For example, you can do this for FPS value from the game loop so the user is able to get the fps but not set it.

Rule #4: Use Setters in case you need data verification.

Yes, I don’t say never use setters, you have to use them when you really need and this is one of such areas. Consider that you have to set a value, like the volume of the playing sound, and it should be in a range.


public void setVolume(float volume)
{
    this.volume = Math.min(1, Math.max(volume, 0));
}

These are the four basic rules that I’ve taught myself recently after reading a lot of sample android code, and they work great for me so I do recommend them to you. Additionally this removes the function call overhead, as I heard (but am not sure) that invoking virtual functions causes some overhead.

just to add my 2 cents SHC’s description …

i think this issue should be a no-brainer. getter/setter (simple, without processing) and field read/write access is the same thing … if using a good IDE, like idea.

you can always track access and refactor all that stuff back and forth by hitting the keyboard with your face (hot-key).

The biggest reasons why I use getters and setters is…

  1. They allow immutable classes to be made, where an object manages its own fields. This is why I use the final keyword a lot. It not only helps me make classes immutable, but allows for me to identify variables in code easier (format highlighting), directs meaning to variables without final (value will change), and catch any errors where I have tried to implement something other than my idea I was trying to write down for a function (trying to overwrite variables unnecessarily).

  2. when it comes time that you want to change whatever.x = 5 to whatever.setX(5), you will need to go back and change all references to whatever.x with whatever.setX(). This isn’t a huge problem in eclipse because of alt shift R. It’s a task if something goes wrong and you end up creating getters and setters.

  3. This goes along with #1. Getters and setters help you with code suggestions. whatever.get (ctrl + space) gives you a list of all variables. When you don’t use getters and setters, the variables are mashed into the functions and have an uncommon name. This makes it hard to search for.

  4. Anonymous inner types can modify your getters and setters as they see fit for the specific application.

An immutable class doesn’t manage its own fields. It’s fields don’t change. Also I think you are confusing final on a method (cannot override) with final on a field (value fixed at instantiation).