By providing getters and setters we get the benefits of hiding the implementation. e.g. You can use lazy initialization, proxies etc.
Code becomes more maintainable e.g. you can easily add pre and post checks (or validations) at one place. If you access the variable directly and later on you need to add any validation or some default behaviour while reading the value you would have to change it at multiple places.
By getters and setters you get the benefits of polymorphism. e.g. if you don't want value of the variable to be changed in extended version or vice versa, you can simply throw exception.
From debugging point of view:
Provides the segregation of code lines where the variable's value is accessed or updated. (Can be used to check references)
Sometimes, we need to know where the value of variable got changed. You can put debug pointer or logger to investigate it.