Reputation: 1561
I wanted to get only one field name of a POJO, my java POJO look like:
public class A1 {
private String field2;
private String field1;
public String getField2() {
return field2;
}
public void setField2(String field2) {
this.field2 = field2;
}
public String getField1() {
return field1;
}
public void setField1(String field1) {
this.field1 = field1;
}
@Override
public String toString() {
return "A1 [field2=" + field2 + ", field1=" + field1 + "]";
}
public String getFiled1Name() throws NoSuchFieldException, SecurityException{
return this.getClass().getDeclaredField(field1).getName();
}
}
In the client code:
System.out.println(new A1().getFiled1Name());
I am getting NullPointerException
I tried method this.getClass().getDeclaredFields()
and this works as expected. But the problem with this is: It returns all the fields(java.lang.reflect.Field
) and I need to iterate, compare and then return the correct filed name.
Rather I want to get only one field name and with no hard coded field name in the method. How I can get this?
Upvotes: 0
Views: 2361
Reputation: 6082
I thought of this, not sure if Thread.currentThread().getStackTrace()
is relaiable enugh, however you want something totally dynamic , no hardcoded... so this is my shoot:
public class Reflections {
private String field2;
private String field1;
public static void main(String[] args) {
Reflections r = new Reflections();
System.out.println(r.getField1Name());
}
private Field fields[] = null;
public Reflections() {
fields = getClass().getDeclaredFields();
}
public String getField1Name() {
if(fields == null || fields.length==0){
return null;
}
final StackTraceElement[] stes = Thread.currentThread().getStackTrace();
if(stes == null || stes.length<2){
return null;
}
final String thisMethodName = stes[1].getMethodName(); // [1] this is supposed to have the name of current method
for (Field f : fields) {
if (thisMethodName.toLowerCase().contains(f.getName().toLowerCase())) {
//System.out.println(f.getName());
return f.getName();
}// match
}// for fields
return null;
}// getFiled1Name
}
in short, getField1Name()
tries to find it's own name,
and then iterates through fields list of current class, and tries to find a field that it's name is part of the method name.
this could return invalid result sometimes, as some field names might be a sub-part of longer name, and some other cases where the result will not be accurate
but however, here it is, maybe it's useful for you or anyone else.
you can refactor the code, creating new method getFieldNameUsingMethodName()
?? maybe ?!?! this will do the loop and match thing, in case you have like 10 or more getFieldXname()
so you can do it if you think this sol worthy.
Upvotes: 0
Reputation: 23002
You should supply name of the field instead of field itself as field1
is String which is null
and you are passing null
to the getDeclaredField
,
public String getFiled1Name() throws NoSuchFieldException, SecurityException {
return getClass().getDeclaredField("field1").getName();
}
Class#getDeclareField
throwsNullPointerException
- if name is null
I don't want to hard code "field1"
You can create a constant for the field name instead of using reflection but for every change in name you also need to update constant.
In other way out you can get all declared fields and access the name of the field from the array. But be careful while using this as change in the declaration may change behavior of the method.
public String getFiled1Name() throws NoSuchFieldException, SecurityException {
return getClass().getDeclaredFields()[0].getName();
}
Upvotes: 4
Reputation: 732
Your field field1 is null. You haven't initialized the String. So that causes the NullPointerException. You're currently just passing null to the getDeclaredField() method.
Upvotes: 0
Reputation: 3115
you need to pass field name as String.
public String getFiled1Name() throws NoSuchFieldException, SecurityException{
return this.getClass().getDeclaredField("field1").getName();
}
Upvotes: 0