API
API(Application Programming Interface) 应用程序编程接口
是一些在Java中已经编写好的类,提供一些已经写好的方法,开发者可以直接调用这些方法而无须知道方法的底层实现过程,提高开发的效率。
Object类
在Java的类层次结构中Object类是一切类的父类,所有的非Object类都继承自Object类,在编译器中如果创建一个新类默认都继承自Object类。
Object类中常用的方法
hashCode()
public int hashCode()
返回对象的哈希码值,哈希码值相当于是一个地址值但不是真正意义上的地址,是Java根据对象的地址或者字符串或者数字算出来的int类型的数值。他的返回值是一个int型的数值,在Java中对同一对象多次调用hashCode()方法返回值相同。
getClass()
public final Class<?> getClass()
返回当前对象所属于的类,如果直接输出会是以Class开头后面跟空格包名.类名,他的返回值是Class形式并不是String类型如下:
class A {
public A() {
super();
}
}
public class Text {
public static void main(String[] args) {
A s = new A();
System.out.println(s.getClass()); //输出为:class text.A
Class c = s.getClass(); // getClass()的返回值是Class形式
System.out.println(c); //输出为:class text.A
}
}
Class<?>它是个通配泛型,?可以代表任何类型。
toString()
public String toString()
返回对象的字符串表示形式。当我们直接输出一个对象的时候其实就是再调用toString()方法如下:
class A {
int age;
String name;
}
public class Text {
public static void main(String[] args) {
A s = new A(); // 创建A类对象s
System.out.println(s);// 输出为text.A@16f65612
System.out.println(s.toString());// 输出为text.A@16f65612
}
}
这里输出的是text.A@16f65612我们可以看toString()的源码来理解
toString方法在Objiect中的定义为:
public String toString() {
return getClass().getName() + "@" + Integer.toHexString(hashCode());
}
getClass().getName()返回的是字符串形式的全类名是包名.类名的形式:text.A,然后拼接了个@,Integer.toHexString()是Integer类中的toHexString()静态方法,返回的是int类型16进制变量的字符串形式。hashCode()返回的是当前对象的哈希码值。所以以下三行代码其实是等效的:
System.out.println(s);
// 输出为text.A@16f65612
System.out.println(s.toString());
// 输出为text.A@16f65612
System.out.println(s.getClass().getName() + "@" + Integer.toHexString(s.hashCode()));
// 输出为text.A@16f65612
但是实际使用中toString()返回的结果应该是一个简明的表达,容易让人阅读。
所以我们在子类中重写toString():
class A {
int age;
String name;
@Override//重写toString()
public String toString() {
return "A [age=" + age + ", name=" + name + "]";
}
public A(int age, String name) {
super();
this.age = age;
this.name = name;
}
public A() {
super();
}
}
public class Text {
public static void main(String[] args) {
A s = new A(21, " 井杰");// 创建A类对象s
System.out.println(s);// 输出为:A [age=21, name= 井杰]
}
}
toString()重写可以通过编辑器自动提供,在eclipse中用SHIFT+ALT+S然后选择Generate toString即可自动重写。
建议在需要使用toString()的类中全部重写toString。
equals(Object obj)
public boolean equals(Object obj)
equals(Object obj)判断两个非空对象是否相等,返回值是boolean类型,在Object中equals的源码如下定义:
public boolean equals(Object obj) {
return (this == obj);
}
可以看到默认情况下比较的是两个对象的地址值,这就导致两个对象必须指向同一个地址时才会返回true,如下:
class A {
int age;
String name;
public A(int age, String name) {
super();
this.age = age;
this.name = name;
}
public A() {
super();
}
}
public class Text {
public static void main(String[] args) {
A a = new A(21, " 井杰");
A b = new A(21, " 井杰");
A c = a;
System.out.println(a.equals(b));// false
System.out.println(a.equals(c));// true
}
}
虽然a,b两个对象给了相同的赋值,但是因为两个对象都是new出来的,所以有各自的地址值所以返回值为false。
这种处理方式不符合我们实际的需求,所以一般在实际使用中我们需要在子类中重写equals方法:
class A {
int age;
String name;
public A(int age, String name) {
super();
this.age = age;
this.name = name;
}
public A() {
super();
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + age;
result = prime * result + ((name == null) ? 0 : name.hashCode());
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
A other = (A) obj;
if (age != other.age)
return false;
if (name == null) {
if (other.name != null)
return false;
} else if (!name.equals(other.name))
return false;
return true;
}
}
public class Text {
public static void main(String[] args) {
A a = new A(21, " 井杰");
A b = new A(21, " 井杰");
A c = a;
System.out.println(a.equals(b));// true
System.out.println(a.equals(c));// true
System.out.println(b.equals(c));// true
System.out.println(a.hashCode());//682471
System.out.println(b.hashCode());//682471
System.out.println(c.hashCode());//682471
}
}
重写equals方法后equals判断依据变为判断两个对象是否有相同的内容,同样这一步可以使用编辑器自动给出,
在eclipse中用SHIFT+ALT+S然后选择Generate hashCode() and equals()..即可自动重写。
一般重写equals的同时还会重写hashCode方法,以便规定相同的两个对象必须返回相同的哈希码值。
clone()
创建并返回此对象的副本。用于复制某个对象,使用方法如下:
class A implements Cloneable {// 使用clone方法时子类需要实现Cloneable接口。
int age;
String name;
public A(int age, String name) {
super();
this.age = age;
this.name = name;
}
public A() {
super();
}
@Override//还需要重写Clone方法,输入Clone然后ALT+/可以自动重写
protected Object clone() throws CloneNotSupportedException {
return super.clone();
}
public void out() {
System.out.println("姓名:" + name);
System.out.println("年龄:" + age);
System.out.println("-----------");
}
}
public class Text {
public static void main(String[] args) throws CloneNotSupportedException {//还需要在main方法添加异常处理
A a = new A(21, "井杰");
Object obj = a.clone();// 调用clone方法复制对象a
A b = (A) obj;// 向下转型
a.out();
b.out();
}
}
/**输出为:
姓名:井杰
年龄:21
-----------
姓名:井杰
年龄:21
-----------
*/
所有的数组都默认实现了Cloneable接口,并且数组类型的clone方法返回值仍然是数组类型。
Class类
class类中常用的方法
getName()
public String getName()
以String形式返回当前类的名称。需要对象为Class形式。如下:
class A {
int age;
String name;
}
public class Text {
public static void main(String[] args) {
A s = new A(); // 创建A类对象s
Class c = s.getClass(); // 返回值是Class形式
System.out.println(c); // 输出为Class形式的类名称:class text.A
System.out.println(c.getName()); // 返回Class形式类名的String形式
String d = c.getName(); // 返回值为String类型。
System.out.println(d); // 输出为:text.A
System.out.println(s.getClass().getName()); // 链式变成写法,输出为:text.A
System.out.println(A.class.getName()); // 也可以用类名.class调用输出为:text.A
}
}
Scanner类
Scanner类是一个简单的文本扫描器,属于java.util包下,使用时需要导包。
扫描控制台输入
Scanner可以扫描控制台的输入,这是Scanner最常见的使用方式:
import java.util.Scanner;//导包,快捷键 ctrl+shift+o
public class Text {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);//创建录入对象
String a = sc.nextLine();//将录入内容转化为String类型赋值给a
System.out.println(a);//输出
}
}
在创建录入对象的时候我们调用了Scanner的一个构造方法:
public Scanner(InputStream source) {
this(new InputStreamReader(source), WHITESPACE_PATTERN);
}
以输入流的形式录入数据,然后接收了System.in提供的输入流。
Scanner类中常用的方法
nextXXX()
将键盘录入的对象转换成我们所需要的形式其中包括:
nextBoolean() | 将输入的内容扫描为boolean类型的值,并返回该值。 |
nextByte() | 将输入的内容扫描为byte类型的值,并返回该值。 |
nextDouble() | 将输入的内容扫描为double类型的值,并返回该值。 |
nextFloat() | 将输入的内容扫描为float类型的值,并返回该值。 |
nextInt() | 将输入的内容扫描为int类型的值,并返回该值。 |
nextLine() | 将输入的内容扫描为String类型的值,并返回该值。 |
nextLong() | 将输入的内容扫描为long类型的值,并返回该值。 |
nextShort() | 将输入的内容扫描为Short类型的值,并返回该值。 |
需要注意:当我们输入了不符合对应类型的内容时会报错。所以Java提供了一个检查的方法。
hasNextXXX()
检查输入内容是否符合当前指定的类型,返回值是boolean类型,如果符合当前制定类型则输出true,同样包含以下方法:
hasNextBoolean() | hasNextFloat() | hasNextLong() |
hasNextByte() | hasNextInt() | hasNextShort() |
hasNextDouble() | hasNextLine() |
使用方式如下:
import java.util.Scanner;
public class ScannerDemo2 {
public static void main(String[] args) {
// 创建键盘录入对象
Scanner sc = new Scanner(System.in);
while (true) {
// 录入数据
System.out.println("请输入一个数据:");
if (sc.hasNextInt()) {// 判断输入是否符合int类型
int num = sc.nextInt();
System.out.println(">>>" + num);
} else {
System.out.println("您输入的数据类型不匹配...");
break;
}
}
}
}
/***
请输入一个数据:
123
>>>123
请输入一个数据:
asd
您输入的数据类型不匹配...
*/
需要注意
1、此种输入方式不支持直接输入char类型,Scanner内并没有nextChar()方法。
2、同一个录入对象连续录入的时候需要用回车隔开,当先录入一个int类型的数据,再录入String类型的数据的时候由于回车本身也属于String类型就会导致第二个数据被跳过此时必须为第二个输入对象创建新的录入对象。
import java.util.Scanner;
public class Text {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
int a = sc.nextInt();
Scanner sc2=new Scanner(System.in);
String b = sc2.nextLine();
System.out.println("a:" + a + ",b:" + b);
}
}
/**
123
qwe
a:123,b:qwe
*/