Java toString()方法

原文:https://www.studytonight.com/java-examples/java-tostring-method

toString()方法是 Object 类的一部分,返回一个对象的字符串表示。这个方法提供了一种用 Java 文本表示对象的方法。所有的 Java 类在内部都继承了对象类。所以,所有的 Java 类都可以覆盖这个方法。

在本教程中,我们将学习 toString()函数。

默认实现

对象类为 toString()方法提供了一个实现。然而,这个实现并没有给出很多关于对象及其字段的信息。它只返回一个包含对象类名和对象 hashcode 的字符串。这两个组件由 @ 隔开。

public String toString()
{
    return getClass().getName()+"@"+Integer.toHexString(hashCode());
}

让我们创建一个类并查看这个方法给出的输出。

class Student
{
    String name;
    double gpa;

    Student(String s, double d)
    {
        this.name = s;
        this.gpa = d;
    }
}
public class Demo
{    
    public static void main(String[] args)
    {
        Student s = new Student("Justin", 8.81);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

学生@7a81197d

注意这个方法也被 System.out.print() 方法隐式调用。下面的代码演示了这一点。

class Student
{
    String name;
    double gpa;

    Student(String s, double d)
    {
        this.name = s;
        this.gpa = d;
    }
}

public class Demo
{    
    public static void main(String[] args)
    {
        Student s = new Student("Justin", 8.81);
        System.out.print(s);// toString() called implicitly
    }
}

学生@7a81197d

覆盖默认实现

如上所述,所有的类都扩展了对象类,它们可以覆盖 toString()方法。默认实现没有提供关于对象字段的大量信息。让我们在学生课上覆盖这个方法。

class Student
{
    String name;
    double gpa;

    Student(String s, double d)
    {
        this.name = s;
        this.gpa = d;
    }    
    //Returning the object fields by overriding toString()
    @Override
    public String toString()
    {
        return "Student[ Name:" + name + " GPA:" + gpa +" ]";
    }
}
public class Demo
{    
    public static void main(String[] args)
    {
        Student s = new Student("Justin", 8.81);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

学生【姓名:贾斯汀 GPA:8.81】

覆盖复杂对象的默认实现

如果我们的类包含对其他对象的引用,那么我们还需要覆盖被引用对象类中的 toString()方法。

例如,让我们向学生类中添加一个地址类字段,并查看覆盖的 toString()方法的输出。

class Student
{
    String name;
    double gpa;
    Address studentAddress;//referenced object

    Student(String s, double d, Address add)
    {
        this.name = s;
        this.gpa = d;
        this.studentAddress = add;
    }
    @Override
    public String toString()
    {
        return "Student[ Name:" + name + " GPA:" + gpa + " Address:" + studentAddress +" ]";
    }
}
class Address
{
    int postalCode;
    Address(int i)
    {
        this.postalCode = i;
    }
}
public class Demo
{    
    public static void main(String[] args)
    {
        Address add = new Address(100012);
        Student s = new Student("Justin", 8.81, add);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

学生【姓名:贾斯汀 GPA:8.81 地址:地址@24d46ca6】

如我们所见,Address 类使用默认实现。我们得到地址类名和对象哈希码,但它不包括邮政编码。我们需要覆盖 Address 类中的 toString()方法来纠正这个问题。

class Student
{
    String name;
    double gpa;
    Address studentAddress;

    Student(String s, double d, Address add)
    {
        this.name = s;
        this.gpa = d;
        this.studentAddress = add;
    }

    //toString() method for Student class
    @Override
    public String toString()
    {
        return "Student[ Name:" + name + " GPA:" + gpa 
                + " Address:" + studentAddress +" ]";
    }
}

class Address
{
    int postalCode;
    Address(int i)
    {
        this.postalCode = i;
    }

    //toString() method for Address class
    @Override
    public String toString()
    {
        return "Address[ Postal Code:" + postalCode +" ]";
    }
}

public class Demo
{    
    public static void main(String[] args)
    {
        Address add = new Address(100012);
        String addressStr = add.toString();
        System.out.println(addressStr);

        Student s = new Student("Justin", 8.81, add);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

地址【邮政编码:100012】 学生【姓名:贾斯汀 GPA:8.81 地址:地址【邮政编码:100012】】

Arrays.toString()方法

Arrays 类还提供了一个 toString()方法来显示数组的内容。如果我们的类包含一个数组数据成员,我们必须在覆盖的 toString()方法中使用 Arrays.toString() 。让我们首先在不使用 Arrays.toString()的情况下查看输出。

class Student
{
    String name;
    double gpa;
    double[] marks;

    Student(String s, double d, double[] marks)
    {
        this.name = s;
        this.gpa = d;
        this.marks = marks;
    }

    //Overriding toString() method without using Arrays.toString()
    @Override
    public String toString()
    {
        return "Student[ Name:" + name + " GPA:" + gpa + " Marks:" + marks + " ]";
    }
}

public class Demo
{    
    public static void main(String[] args)
    {
        double[] marks = {10.5, 12.21, 19.0};
        Student s = new Student("Justin", 8.81, marks);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

学生【姓名:贾斯汀 GPA:8.81 分:【D@5ca881b5】

我们可以看到,显示的是数组的 hashcode,而不是内容。让我们在 toString()方法中使用 Arrays.toString()方法。

import java.util.Arrays;

class Student
{
    String name;
    double gpa;
    double[] marks;

    Student(String s, double d, double[] marks)
    {
        this.name = s;
        this.gpa = d;
        this.marks = marks;
    }

    //Using Arrays.toString()
    @Override
    public String toString()
    {
        return "Student[ Name:" + name + " GPA:" + gpa + " Marks:" + Arrays.toString(marks) + " ]";
    }
}

public class Demo
{    
    public static void main(String[] args)
    {
        double[] marks = {10.5, 12.21, 19.0};
        Student s = new Student("Justin", 8.81, marks);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

学生【姓名:贾斯汀 GPA:8.81 分:【10.5,12.21,19.0】】

还有一个 deepToString() 方法,为多维数组返回合适的字符串表示。

import java.util.Arrays;

public class Demo
{    
    public static void main(String[] args)
    {
        int[][] multiDimArr = {
                {1, 2, 3},
                {4, 5, 6},
                {6, 7, 8},
                {7, 8, 9}
        };
        String multiDimStr = Arrays.deepToString(multiDimArr);
        System.out.print(multiDimStr);
    }
}

[[1,2,3],[4,5,6],[6,7,8],[7,8,9]]

包装器、集合和字符串缓冲区

许多预定义的类都有一个针对 toString()方法的覆盖实现。这是为了确保打印这些类的对象的有意义的字符串表示。如果我们有这些类的数据成员,我们就不需要在被覆盖的 toString()方法中使用任何其他方法。下面的代码演示了这一点。

import java.util.ArrayList;

class Student
{
    StringBuffer name;
    Double gpa;
    ArrayList<Double> marks;

    Student(StringBuffer s, double d, ArrayList<Double> marks)
    {
        this.name = s;
        this.gpa = d;
        this.marks = marks;
    }

    //No need to use any special method for any fields inside the toString() method
    @Override
    public String toString()
    {
        return "Student[ Name:" + name + " GPA:" + gpa + " Marks:" + marks + " ]";
    }
}

public class Demo
{    
    public static void main(String[] args)
    {
        ArrayList<Double> marks = new ArrayList<>();
        marks.add(10.5); marks.add(12.21); marks.add(19.0);
        Student s = new Student(new StringBuffer("Justin"), 8.81, marks);
        String studentDetail = s.toString();
        System.out.print(studentDetail);
    }
}

学生【姓名:贾斯汀 GPA:8.81 分:【10.5,12.21,19.0】】

摘要

对象类提供了一个 toString()方法,该方法返回 Java 对象的字符串表示形式。然而,这个方法在 Object 类中的实现不是很有用。由于这个原因,许多预定义的 Java 类,如整数、双精度、ArrayList、字符串缓冲区覆盖了这个方法。在用户定义的 Java 类中覆盖这个方法也是一个很好的做法。