How to instantiante object & call setter on same line? - java

If I have an Employee class with a default constructor:
private String firstName;
public Employee(){}
and a setter:
public void setFirstName(String firstName){
this.firstName = firstName;
}
Why does this attempt fail to instantiate and call the setter in the same line?
Employee employee = new Employee().setFirstName("John");

You can also use this syntax:
Employee employee = new Employee() {{
setFirstName("John");
}};
Though keep in mind that it's going to create an anonymous inner class and probably isn't what you want.

Because setFirstName doesn't return anything. If you want to chain methods then setFirstName would have to return Employee.
Another approach is to have a constructor that takes firstName as an argument.

(employee = new Employee()).setFirstName("John");
performs instantiation and calling the setter, as you requested in the headline, but does not declare the variable as suggested in your code example.
(Employee employee = new Employee()).setFirstName("John");
will probably not work, I assume. But you can try.
Of course, you can always stuff multiple statements in one line.
Employee employee; (employee = new Employee()).setFirstName("John");
or
Employee employee = new Employee(); employee.setFirstName("John");
If I were you, I would settle for a parameterized constructor, though.

The method serFirstName is of return type void (nothing). Try:
public Employee setFirstName(String fname) {
this.firstName = fname;
return this;
}

It should be like this:
Employee employee = new Employee();
employee.setFirstName("John");

Although this is a bit overkill, you could try using the builder pattern
public class Employee{
private String firstName;
public static class Builder{
private String firstName;
public Builder firstName(String firstName){
this.firstName = firstName;
return this;
}
public Employee build(){
return new Employee(this);
}
}
private Employee(Builder builder){
firstName = builder.firstName;
}
}
Then you can do the following
Employee e = new Employee.Builder().firstName("John").build();

Because the you want to set employee to the value of .setFirstName("John"); which does not return anything because it is a void
So you could either change your setter to:
public Employee setFirstName(String fname) {
this.firstName = fname;
return this;
}
OR Create a second constructor for Employee
public Employee(String fname){this.firstName = fname;}
Which would set firstname on init.

In order for your code to work, you would have to return the Employee (meaning "this") in the setter method setFirstName.
If you don't own the Employee class (I know this is just a simple example - but for the sake of argument) and cannot modify it, one way to solve that is using functional programming. You could declare yourself a function like this:
static final Function<String, Employee> EMPLOYEE = firstName -> {
Employee employee = new Employee();
employee.setFirstName(firstName);
return employee;
};
And then you can create your employee in one line like this:
Employee jake = EMPLOYEE.apply("Jake");
Maybe not exactly what you want, but still useful.

Related

How in JPA mappe into one column values of two other columns?

I am using JPA, and in my DB I have a table student with columns: id, firstname and firstAndLastname
So I did an Entity to mappe data, I can get lastname from another table, but I don't persist it as there is no columns lastname in DB.
How to store in column firstAndLastname that is concatenation of firstname and lastname and store it in specific column, example : firstname : John, lastname : Doe => firstAndLastname : JohnDoe
#Entity
#Table(name = "student")
public class Student implements Serializable {
#Id
#Column(name = "id")
private Integer id;
#Column(name = "firstname")
private String firstname;
#Transient
private String lastname;
#Column(name = "firstAndLastname")
private String firstLastname;
I tried this (and not working) :
public String getFirstLastname() {
return this.firstname+ this.lastname;
}
Any idea ?
Genetate getters/setter for all properties of the Entity.
Instantiate the object to save: Student student = new Student(1,"Mario","Rossi");
Call the setter : student.setFirstLastName(student.getFirstName()+student.getLastName());
myStudentService.save(student);.
If you still haven't figured out how to persist data to the database, that's where you need to start. You don't persist data in the JPA itself, that's just the structure for the object. You will build an instance of the Student object in another Class, set the values, and persist it to the database.
You would set that firstLastName value where/when you are creating an instance of your Student.
This is just a rough explanation. Not explicit code for you.
You would have a class like:
public class SaveStudentService {
public saveStudent(){
Student student = new Student();
student.setFirstName("test");
student.setLastName("lastTest");
student.setFirstLast(student.getFirstName + " "+ student.getLastName);
studentRepo.save(student);
}
}
You'll have your normal getters and setters in your Student class...
public Student getfirstName() {return this.firstName;}
public Student setfirstName(String firstName) {return this.firstName = firstName;}
public Student getfirstLast() {return this.firstLastName;}
public Student setfirstName(String firstLastName) {return this.firstLastName = firstLastName;}
I would recommend 2 approaches:
If you instantiate object by constructor:
public Student(final Integer id, final String firstname, final String lastname) {
this.id = id;
this.firstname = firstname;
this.lastname = lastname;
this.firstLastname = String.join(firstname, lastname);
}
By setter:
public void setFirstLastname(final String firstName, final String lastName) {
this.firstLastname = String.join(firstName, lastName);
}
In addition you can also use Spring AOP and advice save method on your repository but it's less readable and more difficult to maintenance.
#Before("execution(* com.package.StudentRepository.save(..))")
public void updateFirstLastName(final JoinPoint joinPoint) {
final Object[] arguments = joinPoint.getArgs();
// find Student.class object and update firstLastName field
}
Either way - don't perform concatenation outside Student class because it leads to boilerplate and it's harder to maintenance.
But IMHO the best approach is to store firstName and lastName separately in database and use SQL CONCAT function if needed.

How the code is working here in the subclass?

package practice;
class person{
private String firstname;
private String lastname;
public person(String firstname,String lastname){
set_first(firstname);
set_last(lastname);
}
public String get_first() {
return firstname;
}
public void set_first(String firstname) {
this.firstname=firstname;
}
public void set_last(String lastname) {
this.lastname=lastname;
}
public String get_last() {
return lastname;
}
}
class employee extends person {
private int empid;
public employee(String firstname, String lastname, int empid) {
super(firstname,lastname);
set_empid(empid);
}
public void set_empid(int empid) {
this.empid=empid;
}
public int get_empid() {
return empid;
}
}
class testing_super_keyword {
public static void main(String args[]) {
employee emp=new employee("Paul","Anderson",1234);
System.out.println(emp.get_first()+" "+emp.get_last());
System.out.println(emp.get_empid());
}
}
I got two classes here person superclass and employee subclass. So i just wanted to know this code isn't supposed to work as the firstname and lastname variable is private in superclass? But how the subclass i.e employee is inheriting those members and using it??
I thought private variable of superclass cant be inherited so how come it works fine here?
I am totally confused please help......
Although, the private variables of parent class are not inherited by child class i.e employee but there are public functions that are called getter and setter that allows to access the private members of class from its sub-class.
public String get_first() {
return firstname;
}
public void set_first(String firstname) {
this.firstname=firstname;
}
public void set_last(String lastname) {
this.lastname=lastname;
}
public String get_last() {
return lastname;
}
You see when you want to access firstname from parent, you'll call get_first() from employee object to get the firstname. If you want to set the firstname you'll call set_first("name") to set the name. Hope it might help.
private variable of superclass cant be inherited
Yes, you are absolutely right, they won't be inheriting. But in your code, you are not accessing those fields directly right?
public employee(String firstname,String lastname,int empid){
super(firstname,lastname);
set_empid(empid);
}
Here you are passing parameters (from the main method) to your employee constructor, the names of parameters are similar to the fields in person, but they are not the same. You can change parameters names like this and it will still work fine.
public employee(String fName, String lName,int empid){
super(fName,lName);
set_empid(empid);
}
Here the parameter values are taken into super class constructor and its private fields are initialized and then empid of employee is initialized.
System.out.println(emp.get_first()+" "+emp.get_last());
System.out.println(emp.get_empid());
Here also you are not accessing the private fields directly, you are calling the public methods which will be inherited to the employee and can be called on its reference.
Keeping members of a class as private and their behaviours (methods) as public is a part of encapsulation, so that you cannot directly access then but can set and get its value using public methods.
PS : Try to make the getters and setters using the IDE, if it gives the option and try to follow naming conventions for classes and methods.
lets review how firstname and lastname are being initialized here:
in subclass constructor firstname, lastname has been taken
then in the body of constructor by super(firstname,lastname), firstname and lastname pass to the parent (i.e. Person) to be taken care of.
so assume we are now in the parent constructor (Person) so, By calling set_first(firstname) and set_last(lastname) , parameters firstname and lastname is being set in parent class itself with the values which passed from the child constructor (i.e. Employee)
Regarding this description there is no violation.
The violation happens if you want to initialize private variable directly in Employee class as :
public employee(String firstname,String lastname,int empid){
this.firstname=firstname; //Violation
this.lastname=lastname; //Violation
set_empid(empid);
}

JavaFX - new ImageView and set method [duplicate]

If I have an Employee class with a default constructor:
private String firstName;
public Employee(){}
and a setter:
public void setFirstName(String firstName){
this.firstName = firstName;
}
Why does this attempt fail to instantiate and call the setter in the same line?
Employee employee = new Employee().setFirstName("John");
You can also use this syntax:
Employee employee = new Employee() {{
setFirstName("John");
}};
Though keep in mind that it's going to create an anonymous inner class and probably isn't what you want.
Because setFirstName doesn't return anything. If you want to chain methods then setFirstName would have to return Employee.
Another approach is to have a constructor that takes firstName as an argument.
(employee = new Employee()).setFirstName("John");
performs instantiation and calling the setter, as you requested in the headline, but does not declare the variable as suggested in your code example.
(Employee employee = new Employee()).setFirstName("John");
will probably not work, I assume. But you can try.
Of course, you can always stuff multiple statements in one line.
Employee employee; (employee = new Employee()).setFirstName("John");
or
Employee employee = new Employee(); employee.setFirstName("John");
If I were you, I would settle for a parameterized constructor, though.
The method serFirstName is of return type void (nothing). Try:
public Employee setFirstName(String fname) {
this.firstName = fname;
return this;
}
It should be like this:
Employee employee = new Employee();
employee.setFirstName("John");
Although this is a bit overkill, you could try using the builder pattern
public class Employee{
private String firstName;
public static class Builder{
private String firstName;
public Builder firstName(String firstName){
this.firstName = firstName;
return this;
}
public Employee build(){
return new Employee(this);
}
}
private Employee(Builder builder){
firstName = builder.firstName;
}
}
Then you can do the following
Employee e = new Employee.Builder().firstName("John").build();
Because the you want to set employee to the value of .setFirstName("John"); which does not return anything because it is a void
So you could either change your setter to:
public Employee setFirstName(String fname) {
this.firstName = fname;
return this;
}
OR Create a second constructor for Employee
public Employee(String fname){this.firstName = fname;}
Which would set firstname on init.
In order for your code to work, you would have to return the Employee (meaning "this") in the setter method setFirstName.
If you don't own the Employee class (I know this is just a simple example - but for the sake of argument) and cannot modify it, one way to solve that is using functional programming. You could declare yourself a function like this:
static final Function<String, Employee> EMPLOYEE = firstName -> {
Employee employee = new Employee();
employee.setFirstName(firstName);
return employee;
};
And then you can create your employee in one line like this:
Employee jake = EMPLOYEE.apply("Jake");
Maybe not exactly what you want, but still useful.

Create new instance of the class which is coming as string and update the sets methods

Im getting class name (string) and the class have few sets method and
since Its dynamic (I can get any class) I need to use all the sets method and update it with data .
how can I do that ?
To get the class field I'm using the following code
className = obj.getClassName();
Class<?> classHandle = Class.forName(className);
for example here I need to update firstName and last name
public class Person {
private String id;
private String firstName;
private String lastName;
public void setLastName(String lastName) {
this.lastName = lastName;
}
public void setfirstName(String firstName) {
this.firstName = firstName;
}
or different class here i need to set the salary and the job description
public class Job {
private double salery;
private String jobDescr;
public void setSalery(double salery) {
this.salery = salery;
}
public void setJobDescr(String jobDescr) {
this.jobDescr = jobDescr;
}
}
For starters, What you've done is good. I assume you have a Map<String, Object> of the attributes to be set: attributeMap.
//this is OK
className = obj.getClassName();
Class<?> classHandle = Class.forName(className);
//got the class, create an instance - no-args constructor needed!
Object myObject = classHandle.newInstance();
//iterate through all the methods declared by the class
for(Method method : classHandle.getMethods()) {
//check method name
if(method.getName().matches("set[A-Z].*")
//check if it awaits for exactly one parameter
&& method.getParameterTypes().length==1) {
String attributeName = getAttributeName(method.getName());
//getAttributeName would chop the "set", and lowercase the first char of the name of the method (left out for clarity)
//To be extra nice, type checks could be inserted here...
method.invoke(myObject, attributeMap.get(attributeName));
}
}
Of course, a lot of exception handling is to be done, this is just a basic idea of what is to be done...
Recommended reading:
Class
Class.getMethods()
Method
Method.invoke()

Possibilities of creating immutable class in Java

what are possibilities of creating immutable bean in Java. For example I have immutable class Person. What's a good way to create instance and fill private fields. Public constructor doesn't seems good to me because of a lot input parameters will occure as class will grow in rest of application. Thank you for any suggestions.
public class Person {
private String firstName;
private String lastName;
private List<Address> addresses;
private List<Phone> phones;
public List<Address> getAddresses() {
return Collections.unmodifiableList(addresses);
}
public String getFirstName() {
return firstName;
}
public String getLastName() {
return lastName;
}
public List<Phone> getPhones() {
return Collections.unmodifiableList(phones);
}
}
EDIT: Specify question more precisely.
You could use the builder pattern.
public class PersonBuilder {
private String firstName;
// and others...
public PersonBuilder() {
// no arguments necessary for the builder
}
public PersonBuilder firstName(String firstName) {
this.firstName = firstName;
return this;
}
public Person build() {
// here (or in the Person constructor) you could validate the data
return new Person(firstName, ...);
}
}
You can then use it like this:
Person p = new PersonBuilder.firstName("Foo").build();
At first sight it might look more complex than a simple constructor with tons of parameters (and it probably is), but there are a few significant advantages:
You don't need to specify values that you want to keep at the default values
You can extend the Person class and the builder without having to declare multiple constructors or needing to rewrite every code that creates a Person: simply add methods to the builder, if someone doesn't call them, it doesn't matter.
You could pass around the builder object to allow different pieces of code to set different parameters of the Person.
You can use the builder to create multiple similar Person objects, which can be useful for unit tests, for example:
PersonBuilder builder = new PersonBuilder().firstName("Foo").addAddress(new Address(...));
Person fooBar = builder.lastName("Bar").build();
Person fooBaz = builder.lastName("Baz").build();
assertFalse(fooBar.equals(fooBaz));
You should have a look at the builder pattern.
One good solution is to make your fields final, add your constructor private and make use of Builders in your code.
In our project we combined the Builder pattern with a validation framework so that once an object is created we are sure it's immutable and valid.
Here is a quick example:
public class Person {
public static class Builder {
private String firstName;
private String lastName;
private final List<String> addresses = new ArrayList<String>();
private final List<String> phones = new ArrayList<String>();
public Person create() {
return new Person(firstName, lastName, addresses, phones);
}
public Builder setFirstName(String firstName) {
this.firstName = firstName;
return this;
}
public Builder setLastName(String lastName) {
this.lastName = lastName;
return this;
}
public Builder addAddresse(String adr) {
if (adr != null) {
addresses.add(adr);
}
return this;
}
public Builder addPhone(String phone) {
if (phone != null) {
phones.add(phone);
}
return this;
}
}
// ************************ end of static declarations **********************
private final String firstName;
private final String lastName;
private final List<String> addresses;
private final List<String> phones;
private Person(String firstName, String lastName, List<String> addresses, List<String> phones) {
this.firstName = firstName;
this.lastName = lastName;
this.addresses = addresses;
this.phones = phones;
}
public List<String> getAddresses() {
return Collections.unmodifiableList(addresses);
}
public String getFirstName() {
return firstName;
}
public String getLastName() {
return lastName;
}
public List<String> getPhones() {
return Collections.unmodifiableList(phones);
}
}
In my example you can see that all the setters in the Builder return the Builder instance so that you can easily chain the setters calls. That's pretty useful.
You could take a look at the Builder pattern presented by Joshua Bloch.
As I said before, combined with a validation framework (see for ex. http://www.hibernate.org/subprojects/validator.html) this is really powerfull.
With interfaces. Do this:
public interface Person {
String getFirstName();
String getLastName();
// [...]
}
And your implementation:
// PersonImpl is package private, in the same package as the Factory
class PersonImpl {
String getFirstName();
void setFirstName(String s);
String getLastName();
void setLastName(String s);
// [...]
}
// The factory is the only authority to create PersonImpl
public class Factory {
public static Person createPerson() {
PersonImpl result = new PersonImpl();
// [ do initialisation here ]
return result;
}
}
And never expose the implementation to the places where you want Person to be immutable.
Initializing in the constructor is nevertheless the simplest and safest way to achieve immutability, as this is the only way to have final fields in your immutable class (which is the standard idiom, and has beneficial effects especially if your class is used in a multithreaded environment). If you have lots of properties in your class, it may be a sign that it is trying to do too much. Consider dividing it to smaller classes, or extracting groups of related properties into compound property classes.
Using a Builder (with a private constructor) is a possibility, however it still needs a way to set the properties of the object being built. So you fall back to the original dilemma of constructor parameters vs accessing the private members. In the latter case you can't declare the properties of the object being built as final, which IMHO is a great minus. And in the former case you still have the same long list of constructor parameters you wanted to avoid in the first place. Just now with a lot of extra boilerplate code on top of it.
You can achieve an "immutable" bean by making a read-only interface and then making the implementation into a mutable bean. Passing around the interface won't allow for mutation, but when you construct the object and have the implementation, you can do all sorts of bean-y things:
public interface Person {
String getFirstName();
String getLastName();
// ... other immutable methods ...
}
public class MutablePerson implements Person {
// ... mutable functions, state goes here ...
}
Use the factory-pattern:
let Person be an interface with only "get"-functions
create a PersonFactory with an appropriate API for building a Person-object
the PersonFactory creates an object which implements the Person-interface and returns this
Have final fields.
Make the class as "final" class by declaring as final public class Person
do not use setXXX() methods to set the value since it will change the state of a variable. however getXXX() methods are allowed.
Use a private constructor so that you can set fields using the constructor itself.
Follow the above guidelines for Immutable class.
Use final fields for all your instance variables. You can create a constructor if you like and choose to not expose setters, e.g.,
public class Person {
private final String firstName;
....
public Person(String firstName, ... ) {
this.firstName = firstName;
}
}

Categories