重写toString()函数
一个普通的类,为重写toString函数之前,直接输出该类的对象,结果如下:
package blogTest;
class Test{
public int age;
public double acount;
public String string;
public void setAge(int age) {
this.age = age;
}
public void setAcount(double acount) {
this.acount = acount;
}
public void setString(String string) {
this.string = string;
}
public int getAge() {
return age;
}
public double getAcount() {
return acount;
}
public String getString() {
return string;
}
}
public class ToString {
public static void main(String[] args) {
// TODO Auto-generated method stub
Test test=new Test();
test.setAge(10);
test.setAcount(20.0);
test.setString("hello wolrd!");
System.out.println("test:\t\t\t"+test);//blogTest.Test@2a139a55
System.out.println("test.toString():\t"+test.toString());//未重写toString:blogTest.Test@2a139a55
}
}
/*
结果如下:
test: blogTest.Test@2a139a55
test.toString(): blogTest.Test@2a139a55
*/
注:
当你要输出一个对象的时候。默认调取该对象的toString方法。 每个类默认继承Object对象,它里面的toString方法源码如下:
public String toString() {
return getClass().getName() + "@" + Integer.toHexString(hashCode());
}
getClass().getName()为反射获取类名称 hashCode()为本地方法,返回对象的地址值。
因此输出结果如上图所示。
重写该类的toStirng方法之后
package blogTest;
class Test{
public int age;
public double acount;
public String string;
public void setAge(int age) {
this.age = age;
}
public void setAcount(double acount) {
this.acount = acount;
}
public void setString(String string) {
this.string = string;
}
public int getAge() {
return age;
}
public double getAcount() {
return acount;
}
public String getString() {
return string;
}
@Override
public String toString() {
// TODO Auto-generated method stub
return "年龄:"+age+"\t余额:"+acount+"\t名字:"+string;
}
}
public class ToString {
public static void main(String[] args) {
// TODO Auto-generated method stub
Test test=new Test();
test.setAge(10);
test.setAcount(20.0);
test.setString("hello wolrd!");
System.out.println("test:\t\t\t"+test);//blogTest.Test@2a139a55
System.out.println("test.toString():\t"+test.toString());//为重写toString:blogTest.Test@2a139a55
}
}
/*
结果如下:
test: 年龄:10 余额:20.0 名字:hello wolrd!
test.toString(): 年龄:10 余额:20.0 名字:hello wolrd!
*/
此外我们可以用不同的方法来书写toString()方法,上面已经给了一种直接返回字符串的形式,下面给出另外两种。
--------------方法一----------
用StringBuffer类
package blogTest;
class Test{
public int age;
public double acount;
public String string;
public void setAge(int age) {
this.age = age;
}
public void setAcount(double acount) {
this.acount = acount;
}
public void setString(String string) {
this.string = string;
}
public int getAge() {
return age;
}
public double getAcount() {
return acount;
}
public String getString() {
return string;
}
@Override
public String toString() {
// TODO Auto-generated method stub
// return "年龄:"+age+"\t余额:"+acount+"\t名字:"+string;
StringBuffer stringBuffer=new StringBuffer();
stringBuffer.append("年龄:"+age);
stringBuffer.append("\t余额:"+acount);
stringBuffer.append("\t名字:"+string);
return stringBuffer.toString();
}
}
public class ToString {
public static void main(String[] args) {
// TODO Auto-generated method stub
Test test=new Test();
test.setAge(10);
test.setAcount(20.0);
test.setString("hello wolrd!");
System.out.println("test:\t\t\t"+test);//blogTest.Test@2a139a55
System.out.println("test.toString():\t"+test.toString());//为重写toString:blogTest.Test@2a139a55
}
}
/*
结果如下:
test: 年龄:10 余额:20.0 名字:hello wolrd!
test.toString(): 年龄:10 余额:20.0 名字:hello wolrd!
*/
------------方法二---------
利用反射重写toString方法。
package blogTest;
import java.lang.reflect.Field;
class Test{
public int age;
public double acount;
public String string;
public void setAge(int age) {
this.age = age;
}
public void setAcount(double acount) {
this.acount = acount;
}
public void setString(String string) {
this.string = string;
}
public int getAge() {
return age;
}
public double getAcount() {
return acount;
}
public String getString() {
return string;
}
public void test() {
Class clazz=this.getClass(); // 获取该类的class对象
Field[] fields=clazz.getDeclaredFields(); //获取该类的所有成员变量
System.out.println("输出该类的成员变量:");
for (Field field : fields) {
// System.out.println(field);
/*
* public int blogTest.Test.age
public double blogTest.Test.acount
public java.lang.String blogTest.Test.string
/
try {
System.out.println(field.getName()+":"+field.get(this));
} catch (IllegalArgumentException | IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
/age
acount
string*/
}
}
@Override
public String toString() {
Class clazz=this.getClass(); // 获取该类的class对象
StringBuffer stringBuffer=new StringBuffer();
Field[] fields=clazz.getDeclaredFields(); //获取该类的所有成员变量
for (Field field : fields) {
try {
stringBuffer.append(field.getName()+":"+field.get(this)+"\t");
} catch (IllegalArgumentException | IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}//for
return stringBuffer.toString();
}//toString
}//别忘了这个!!!
/*
- The method main cannot be declared static; static methods can only be declared in a static or top level type
*/
public class ToString {
public static void main(String[] args) {
// TODO Auto-generated method stub
Test test=new Test();
test.setAge(10);
test.setAcount(20.0);
test.setString("hello wolrd!");
System.out.println("test:\t\t\t"+test);//blogTest.Test@2a139a55
System.out.println("test.toString():\t"+test.toString());//为重写toString:blogTest.Test@2a139a55
// test.test();
}
}
/*
输出结果:
test: age:10 acount:20.0 string:hello wolrd!
test.toString(): age:10 acount:20.0 string:hello wolrd!
*/
注:里面的test方法之前忘记了怎么用反射获取成员变量名和成员变量值,用来尝试用的,可以不用管它。
总结:
在这里我们可以看出,使用反射重写toString方法最为麻烦,但是如果添加了新的成员变量不需要重新修改。
不过好像别人说用反射来获取成员变量或者成员方法不好,违背了类的封闭性。╮(╯_╰)╭
下面解释一下:这个简单有注释的。
Class clazz=this.getClass(); // 获取该类的class对象
StringBuffer stringBuffer=new StringBuffer();
Field[] fields=clazz.getDeclaredFields(); //获取该类的所有成员变量
这个主要是遍历成员变量
field.getName()可以获取成员变量的名称; field.get(this)可以获取在这里成员变量值
这里我们用前面用到的StringBuffer类把它串在一起就可以了。
注意抛出异常。
for (Field field : fields) {
try {
stringBuffer.append(field.getName()+":"+field.get(this)+"\t");
} catch (IllegalArgumentException | IllegalAccessException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}//for
注:
哎,这里写的时候犯了一个很愚蠢的错误,main()函数这里报了个错:
The method main cannot be declared static; static methods can only be declared in a static or top level type
百思不得其解。
最后发现居然是修改的时候不小心把上边class类的{}右边的大括号给注释掉了,原来是少了个大括号。