Initializing Fields Value in Constructor Versus in Fields Declaration [duplicate] - java

This question already has answers here:
Initialize class fields in constructor or at declaration?
(16 answers)
Closed 9 years ago.
As we know, in java and some other object-oriented programming languages, fields value can be set in constructor or be initialized in fields declaration statements. I want to know the essential differences between the two ways above. And what conditions I should initialze fields by constructor and what condtions I should't.
Thanks for your help.

The advantage with an argumented constructors is that you can set the field values as per the inputs but you cant do the same with initialized fields.
So if you want to create different objects with different attribute values then go for constructors with arguements. And assign the values of instance variables in your constructor.
If you simply want all the instance variables to have some default value, then assign the values at declaration.

The convention is to initalize a field in the constructor. A constructor is there to essentially build the object. It only follows that building implies the instanciation, or assignment, of it's members. It also means that all your logic for creating the object is in one place, which is desirable. For example..
public NewObj(String something, int somethingElse)
{
this.something = something;
this.somethingElse = somethingElse;
// All the logic is in one place. This is especially useful
// when dealing with huge classes.
}
We follow the conventions like this so when another programmer looks at our work, they will know instantly where to look for the logic that creates the class. By placing it in the field declarations (or worse, in both the field declarations and the constructor) you are confusing that convention.
Exceptions I've seen
When creating static final variables in a class, I've found that they are usually created in the field declaration. For example..
public class NewObj
{
public static final int EMPTY_OBJ = 1;
public static final int SPECIAL_OBJ = 2;
}

final fields are preferred as they are easier to reason about and final fields can only be set in the constructor. I suggest fields which mandatory should be in the constructor.
If you have fields which you want to be able to change later, use setters.
If you have to set the fields by name, there is no easy way to this with a constructor. There is the #ConstructorProperties but few class have implemented this. Java 8 wills support access to argument names via reflection, but for now setters are easier.
Note: there are two alternatives.
You can use static factory methods. This can not only have meaningful names but can return sub-classes
You can use a builder class. This gives you more options for how you define and constructor your object. This is particularly useful if you have lots of mandatory fields.

Using Constructors with Arguments , you can initialize the fields during the object creation with the input custom values provided.
This is often helpful when you want fields to have different values .
For Example:
class Employee{
String mName;
Employee(String name)
{
mName=name;
}
This can help you to initialize Employee names easily while creating Employee Object.

Related

What is the need of private variable with public method in encapsulation? rather then direct declare public variable [duplicate]

This question already has answers here:
Why use getters and setters/accessors?
(37 answers)
Closed 6 years ago.
I know this is very basic but I want to know why we should use private variable in encapsulation.I am mentioning my code. so I can give you better explanation.
Class Employee
{
private String eName;
public String getEname()
{
return this.eName;
}
public void setEname(String name)
{
this.eName=name;
}
Here "eName" is private so we can restrict outside object to access directly. variable can be access using its getter setter only.
Now my question is why we should use getter setter method? can't we declare variable as a public.?
Using setter method any one can change the value so what is need of this private variable?
Another Question
we set create read/write only method if we don't create getter method then it become write only and if we don't create setter method then it become read only.
so what is the use of read only and write only ?
If we don't create setter method then how value will set to variable ?
If we don't create getter method then how value will retrieve?
Please give me the answer of above simple questions.
Thank you
:)
The point of making variable private and
Let's say your bankBalance is a private variable and checkBalance() is a public method which is calling a public getter method getbankBalance() for bankBalance.
Now by doing this I can call checkBalance() which will call getbankBalance() function and read the value of bankBalance. I will only have read only access to sensitive data via a public method only.
Now, If the variable bankBalance is public any function can access and change the value of your bank balance, I can check for packageName.ClassName.bankBalance variable and then I can change the value of that variable to 0.
In order to provide read/write only accesses we need to make variables private, protected.
Hence The need of private variables in public methods.
Hope this is good explanation.
If we declare the method as public, then others can change its value. Sometimes, in encapsulation, you don't want the value to be changed, but only to be seen. public members can be read, as well as be changed. Hence, you declare it private.
so what is the use of read only and write only ?
I have rarely seen write only, but read only is common, for example, in bank account softwares. You want the account balance to be read, but not to be changed!
If we don't create setter method then how value will set to variable ?
obj.eName = "Whatever";
If we don't create getter method then how value will retrieve?
whatever = obj.eName;
in setter we can validate input data being set to property and take action accordingly, refer below :
public void setEname(String name)
{
//Here we can validate input data or even throw an exception
if(name!=null && name.length()<5){
this.eName="Some Default Value";
//throw new IllegalArgumentException("Your custom message goes here");
}else{
this.eName=name;
}
}
Also many api's use java reflection to set private property values, for this setter methods are required.
Now my question is why we should use getter setter method? can't we
declare variable as a public.?
Using setter method any one can change the value so what is need of
this private variable?
The public and protected methods of your classes form part of its exported API, i.e. the contract you make with client users of your class that specifies what your class does. In other words, the accessible methods specify your class's behavior.
The fields of yout class form its state. A class's state need not, and often does not, have a dependency on its contract. In other words, the fields in your class that are hidden away form part of your class's implementation (but not its behavior or its contract).
Note that the hidden parts of an implementation are not part of the contract and are also not part of the exported API. This means that you are free to change the implementation at any time without risk of breaking your client's programs as long as the implementation continues to obey the contract of your exported API. Therefore, fields that make up the state of your objects should nearly always be made private or package-private.
All this changes when you make your fields public. In this case, clients have direct access to your class's state and so now it becomes part of the exported API. Making fields public makes your implementation part of your contract and so now you are no longer free to make any changes to that part of it. You must continue to support that public variable for as long as your class exists.

Basic about function in OOP Java

public void setTo(String to) {
this.to = to;
}
public String getTo() {
return to;
}
What does above code do? In my project file I search for setTo function and there's no setTo() found, so how does it been called? and the this refer to?
In Object Oriented programming it is wrong for other classes to have access to some variables in your program simply because as you write larger programs some of your variables can be changed without your knowledge. To stop this we make the variables in your class private and create getters and setters. The first method is a setter which can set a private variable in your class to what the user wants. This will stop many errors from occurring. The
this
is a keyword which is calling the current class you are in. If the variable passed in as a parameter is the same as the private variable declared at the top of your class, we use this to refer to the variable at the top of the class.
This two methods are the setter-getter for the property to of your class.
You source code may not call these method but still these methods are called by some framework/third party library such as JSF, Spring those you are using in your project.
Looks like you have three questions. I'll answer them in order:
What does above code do?
These methods allow code from outside the class to set and retrieve the to variable value within the class, even if it's been declared private.
In my project file I search for setTo function and there's no setTo() found, so how does it been called?
Spring uses the setter methods to do dependency injection. Basically there's Java in Spring libraries that will automatically look for these variable names and call a corresponding method named after the variable, with 'set' in front of the name.
IDEs can generate both getters and setters automatically, and since you need the setters for Spring, people tend to also have the IDE generate the getters, even if they don't plan on using them.
and the this refer to?
this is a scoping keyword.
this.to refers to a variable named to that's part of the class where these getter/setter methods are. The 'to' without the 'this.' refers to the (String to) in the parameter definition, which is the one that a call would pass in.
Essentially, "Getters" and "Setters" are methods specifically designed to interact with Fields without directly manipulating the field. This is called " FieldEncapsulation"
https://en.wikipedia.org/wiki/Field_encapsulation
Instead of directly accessing a Field, you access it's methods. You can restrict usage in your code, i.e., not allow any getting, or setting, or both.
If you have access to the Field itself, you can do anything, but if you split up methods for the field, then you are able to
better manipulate the field actions.
make your code cleaner (text.setName(name) is easier to understand than writing text = "name";
restrict access to parts of your code (depending who is using your code).
Some pieces of code also use the getters/setters specifically, and not the fields, so making sure your fields have Getters/Setters is a good practice overall.
For example, Apache BeanUtils.copyBean() will NOT copy a bean if getters/setters are not set.
You asked what
public void setTo(String to) {
this.to = to;
}
public String getTo() {
return to;
}
means so instead of saying
String setTo = "hello";
or
String setTo2 = setTo;
you can do
setTo("hello");
or
String s2 = getTo();
So setTo requires a String parameter, and then will get our "to" field String to; to whatever is the value of the parameter.
getTo will then get our field to, and return it.
There are also instances where people will add additional code into the set/get statements, but I'm not sure how common that is.
Hope this helps!
These are Getter and Setter methods for a Class global String variable (or property) named 'to'. The related Class is usually the very same Class the getter and setter methods are contained in as is the variable they are related to. If you look at the top of the Class code just under the Class constructor you should be able to locate the String variable 'to', for example:
private String to = ""; // or something similar
Usually, if there is a variable named 'to' there is also another variable named 'from' (but not always) and it to may also have getter and setter methods contained within the class.
Getter and Setter methods allow you to retrieve and modify variable data contained within a Class from another Class during run-time, for example:
MySpecialClass myClass = new MySpecialClass();
// Use the 'to' variable getter to retrieve its current
// contents and place those contents into the 'toVar' variable.
String toVar = myClass.getTo();
// Display the contents...
System.out.println(toVar);
// Set the 'to' variable within the MySpecialClass Class
// to hold the string "I hold this now"...
myClass.setTo("I hold this now");
// Use the 'to' variable getter again to retrieve its new
// contents and place those contents into the 'toVar' variable.
toVar = myClass.getTo();
// Display the contents again...
System.out.println(toVar);
Now code contained within the MySpecialClass can use the 'to' variable with its new data value. You will notice that Java Class Libraries do things this way, very much the same as setting specific properties for a JButton or JLabel etc. etc.

using a variable in two different java classes

I was wondering if it's possible to use a variable of a java class in another java class.Suppose variable Time is defined and calculated in Class A, how can I use it in Class B?
Other answers have suggested increasing a variable's visibility. Don't do this. It breaks encapsulation: the fact that your class uses a field to store a particular piece of information is an implementation detail; you should expose relevant information via the class's API (its methods) instead. You should make fields private in almost all cases.
Likewise, some other answers have suggested possibly making the variable static. Don't do this arbitrarily. You need to understand what static really means: it's saying that this piece of information is related to the type rather than to any one particular instance of the type. Occasionally that's appropriate, but it's generally a road towards less testable code - and in many cases it's clearly wrong. For example, a Person class may well have a name variable, but that certainly shouldn't be static - it's clearly a piece of information about a single person.
You should think carefully before exposing information anyway - consider whether there's a wider operation which the class in question could expose, instead of just giving away its data piecemeal - but when you do want to expose a field's value, use a property. For example:
public class Person {
private final String name;
public Person(String name) {
this.name = name;
}
public String getName() {
return name;
}
}
By exposing it via a method, you can later change the implementation details without breaking existing clients.
Then from another class, you'd just call the getName() method:
// However you end up getting a reference to an instance of Person
Person person = ...;
String name = person.getName();
If you do have a static field, you can expose the value in the same way, but with a static method, which you'd call using the class name.
Be careful about returning values which are mutable, e.g. java.util.Date. This is another reason for using a getter method instead of allowing direct access to the field - you can make the method return a defensive copy where you need to.
If it is declared as public, you may use ClassA.yourVariable. On the other hand, for private access modifier, include the getter to your ClassA. On the ClassB, call ClassA.getYourVariable().
Also read about access specifiers in Java it might help.
If the variable is static, you can refer to it as A.Time from any code that has access to the variable. There's only one Time value for all of class A. If it is an instance variable, and you have an instance a of class A, you can refer to the variable as a.Time. There's a separate value for each instance of class A.
This is subject to Java's access rules:
if the field is public, any code can access it (this makes public variables kind of dangerous unless they are also declared final)
if the field is protected, only code in the same package or in a subclass of A can access it
if the field has default access, only code in the same package as class A can access it
if the field is private, only code in class A (including inner classes of A) can access it.
Alternatively, you can provide an accessor method in class A:
public class A {
. . .
public class getTime() {
return this.Time; // the "this." is optional
}
}
If you declare your Variable as public or static you will be able to access it from another class.
WHICH IS A VERY VERY BAD IDEA :)

Object Oriented, passing variables or using object state

Hi apologies for the basic question, im sure I've been told the answer before and I've spent some time searching but couldn't find a good answer (probably because its hard to phrase as a search query), I've done a little bit of OO programming before but ive done a lot of procedural stuff recently so that seems to be clouding my thoughts.
I have a program that has to work with strings, part of that program involves sanitising a string, so I have this method:
private void sanitizeString() {
removeEscape();
removePunctuation();
removeCaps();
}
And earlier in the class declared the variable
String x = "... some string ..."
In procedural you would obviously pass all of the functions the string that they need to work on, my question is in OO is it ok to have this string declared at the top of the class and then just do something like
private void removeCaps() {
x = x.toLowerCase();
}
or should it be
private String removeCaps(String y) {
y = y.toLowerCase();
return y;
}
I think this it should be the first way, and I know that that works ok, but im doing something that has to demonstrate good OO so I just want to check I have my basic assumptions right.
Thanks
You have a trade off here:
Declaring the variable as a class variable means that you must create a new object for each String you want to sanitize.
Passing the String variable to each method means that you can reuse the same object to sanitize multiple Strings.
You must weigh the advantages and disadvantages of each approach to decide which is most appropriate for your particular situation.
Since x is declared as class variable, this one is fine:
private void removeCaps() {
x = x.toLowerCase();
}
as class variables are accessible inside class methods and you don't need to pass the class variables as arguments to same class methods
Same class variables are accessed this way only. Very simple example could be POJO classes, where you declare class variables and expose them through getter/setter methods. You don;t need to pass the class variables to these methods and some time, you can't(e.g. in getter methods).
Adding some thoughts around class variable vs. local variable in the method.
If there is a need of a variable which is theoretically associated with the class definition then the variable should be defined as class variable. e.g. employeeId, employeeName.. variables in a employee class should be defined as Employee class variables.
If there are variable needs which are local to a class method only and not required anywhere outside the method/class, then it should be defined as local variable inside the method.
If you are defining some utility methods to respond using some variables then those variables should be passed as argument to the util methods.
Back to your question:
If you are defining a entire class e.g. Sanitising, which has several methods around the string variable e.g. String class itself, then better to define your string as class variable and write the methods using the class variables.
But if you are defining Sanitising as a util/helper class then better to pass the string as method argument as normally you don;t want your util methods to be statefull (associated with the class instance).
To demonstrate good OO, you should definitly use
private String removeCaps(String y) {
return y.toLowerCase();
}
You can pass your Object, in this case your String in the global field x to the method as parameter. The String is then in the local field y and return the modified version.

Initialize class fields in constructor or at declaration?

I've been programming in C# and Java recently and I am curious where the best place is to initialize my class fields.
Should I do it at declaration?:
public class Dice
{
private int topFace = 1;
private Random myRand = new Random();
public void Roll()
{
// ......
}
}
or in a constructor?:
public class Dice
{
private int topFace;
private Random myRand;
public Dice()
{
topFace = 1;
myRand = new Random();
}
public void Roll()
{
// .....
}
}
I'm really curious what some of you veterans think is the best practice. I want to be consistent and stick to one approach.
My rules:
Don't initialize with the default values in declaration (null, false, 0, 0.0…).
Prefer initialization in declaration if you don't have a constructor parameter that changes the value of the field.
If the value of the field changes because of a constructor parameter put the initialization in the constructors.
Be consistent in your practice (the most important rule).
In C# it doesn't matter. The two code samples you give are utterly equivalent. In the first example the C# compiler (or is it the CLR?) will construct an empty constructor and initialise the variables as if they were in the constructor (there's a slight nuance to this that Jon Skeet explains in the comments below).
If there is already a constructor then any initialisation "above" will be moved into the top of it.
In terms of best practice the former is less error prone than the latter as someone could easily add another constructor and forget to chain it.
I think there is one caveat. I once committed such an error: Inside of a derived class, I tried to "initialize at declaration" the fields inherited from an abstract base class. The result was that there existed two sets of fields, one is "base" and another is the newly declared ones, and it cost me quite some time to debug.
The lesson: to initialize inherited fields, you'd do it inside of the constructor.
The semantics of C# differs slightly from Java here. In C# assignment in declaration is performed before calling the superclass constructor. In Java it is done immediately after which allows 'this' to be used (particularly useful for anonymous inner classes), and means that the semantics of the two forms really do match.
If you can, make the fields final.
Assuming the type in your example, definitely prefer to initialize fields in the constructor. The exceptional cases are:
Fields in static classes/methods
Fields typed as static/final/et al
I always think of the field listing at the top of a class as the table of contents (what is contained herein, not how it is used), and the constructor as the introduction. Methods of course are chapters.
In Java, an initializer with the declaration means the field is always initialized the same way, regardless of which constructor is used (if you have more than one) or the parameters of your constructors (if they have arguments), although a constructor might subsequently change the value (if it is not final). So using an initializer with a declaration suggests to a reader that the initialized value is the value that the field has in all cases, regardless of which constructor is used and regardless of the parameters passed to any constructor. Therefore use an initializer with the declaration only if, and always if, the value for all constructed objects is the same.
There are many and various situations.
I just need an empty list
The situation is clear. I just need to prepare my list and prevent an exception from being thrown when someone adds an item to the list.
public class CsvFile
{
private List<CsvRow> lines = new List<CsvRow>();
public CsvFile()
{
}
}
I know the values
I exactly know what values I want to have by default or I need to use some other logic.
public class AdminTeam
{
private List<string> usernames;
public AdminTeam()
{
usernames = new List<string>() {"usernameA", "usernameB"};
}
}
or
public class AdminTeam
{
private List<string> usernames;
public AdminTeam()
{
usernames = GetDefaultUsers(2);
}
}
Empty list with possible values
Sometimes I expect an empty list by default with a possibility of adding values through another constructor.
public class AdminTeam
{
private List<string> usernames = new List<string>();
public AdminTeam()
{
}
public AdminTeam(List<string> admins)
{
admins.ForEach(x => usernames.Add(x));
}
}
What if I told you, it depends?
I in general initialize everything and do it in a consistent way. Yes it's overly explicit but it's also a little easier to maintain.
If we are worried about performance, well then I initialize only what has to be done and place it in the areas it gives the most bang for the buck.
In a real time system, I question if I even need the variable or constant at all.
And in C++ I often do next to no initialization in either place and move it into an Init() function. Why? Well, in C++ if you're initializing something that can throw an exception during object construction you open yourself to memory leaks.
The design of C# suggests that inline initialization is preferred, or it wouldn't be in the language. Any time you can avoid a cross-reference between different places in the code, you're generally better off.
There is also the matter of consistency with static field initialization, which needs to be inline for best performance. The Framework Design Guidelines for Constructor Design say this:
✓ CONSIDER initializing static fields inline rather than explicitly using static constructors, because the runtime is able to optimize the performance of types that don’t have an explicitly defined static constructor.
"Consider" in this context means to do so unless there's a good reason not to. In the case of static initializer fields, a good reason would be if initialization is too complex to be coded inline.
Being consistent is important, but this is the question to ask yourself:
"Do I have a constructor for anything else?"
Typically, I am creating models for data transfers that the class itself does nothing except work as housing for variables.
In these scenarios, I usually don't have any methods or constructors. It would feel silly to me to create a constructor for the exclusive purpose of initializing my lists, especially since I can initialize them in-line with the declaration.
So as many others have said, it depends on your usage. Keep it simple, and don't make anything extra that you don't have to.
Consider the situation where you have more than one constructor. Will the initialization be different for the different constructors? If they will be the same, then why repeat for each constructor? This is in line with kokos statement, but may not be related to parameters. Let's say, for example, you want to keep a flag which shows how the object was created. Then that flag would be initialized differently for different constructors regardless of the constructor parameters. On the other hand, if you repeat the same initialization for each constructor you leave the possibility that you (unintentionally) change the initialization parameter in some of the constructors but not in others. So, the basic concept here is that common code should have a common location and not be potentially repeated in different locations. So I would say always put it in the declaration until you have a specific situation where that no longer works for you.
There is a slight performance benefit to setting the value in the declaration. If you set it in the constructor it is actually being set twice (first to the default value, then reset in the ctor).
When you don't need some logic or error handling:
Initialize class fields at declaration
When you need some logic or error handling:
Initialize class fields in constructor
This works well when the initialization value is available and the
initialization can be put on one line. However, this form of
initialization has limitations because of its simplicity. If
initialization requires some logic (for example, error handling or a
for loop to fill a complex array), simple assignment is inadequate.
Instance variables can be initialized in constructors, where error
handling or other logic can be used.
From https://docs.oracle.com/javase/tutorial/java/javaOO/initial.html .
I normally try the constructor to do nothing but getting the dependencies and initializing the related instance members with them. This will make you life easier if you want to unit test your classes.
If the value you are going to assign to an instance variable does not get influenced by any of the parameters you are going to pass to you constructor then assign it at declaration time.
Not a direct answer to your question about the best practice but an important and related refresher point is that in the case of a generic class definition, either leave it on compiler to initialize with default values or we have to use a special method to initialize fields to their default values (if that is absolute necessary for code readability).
class MyGeneric<T>
{
T data;
//T data = ""; // <-- ERROR
//T data = 0; // <-- ERROR
//T data = null; // <-- ERROR
public MyGeneric()
{
// All of the above errors would be errors here in constructor as well
}
}
And the special method to initialize a generic field to its default value is the following:
class MyGeneric<T>
{
T data = default(T);
public MyGeneric()
{
// The same method can be used here in constructor
}
}
"Prefer initialization in declaration", seems like a good general practice.
Here is an example which cannot be initialized in the declaration so it has to be done in the constructor.
"Error CS0236 A field initializer cannot reference the non-static field, method, or property"
class UserViewModel
{
// Cannot be set here
public ICommand UpdateCommad { get; private set; }
public UserViewModel()
{
UpdateCommad = new GenericCommand(Update_Method); // <== THIS WORKS
}
void Update_Method(object? parameter)
{
}
}

Categories

Resources