枚举类enumeration(enum)
枚举是一组常量的集合。也就是说枚举属于一种特殊的类,里面只包含一组有限的特定的对象。
自定义枚举类
实现方法:
- 将构造器私有化,防止直接new出来
- 去掉set方法,防止属性被修改
- 直接在内部创建固定的对象
- 对外暴露对象(通过为对象添加 public static 修饰符)
- 优化:加入一个final修饰符
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36
| public class Season { private String name; private String desc;
private Season(String name, String desc) { this.name = name; this.desc = desc; }
public static final Season SPRING = new Season("春天", "温暖"); public static final Season SUMMER = new Season("夏天", "炎热"); public static final Season AUTUMN = new Season("秋天", "凉爽"); public static final Season WINTER = new Season("冬天", "寒冷");
public String getName() { return name; }
public String getDesc() { return desc; }
@Override public String toString() { return "Season{" + "name='" + name + '\'' + ", desc='" + desc + '\'' + '}'; } }
public static void main(String[] args) { System.out.println(Season.SPRING); }
|
使用enum关键字生成枚举类
实现方法:
- 使用关键字enum替代class
- public static final Season SPRING = new Season(“春天”, “温暖”); -> SPRING(“春天”, “温暖”); 即:常量名(实参列表);
- 如果有多个常量(对象),使用逗号间隔,最后一个用分号
- 定义的常量对象必须写在最前面
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36
| public enum Season01 { SPRING("春天", "温暖"), SUMMER("夏天", "炎热"), AUTUMN("秋天", "凉爽"), WINTER("冬天", "寒冷");
private String name; private String desc;
private Season01(String name, String desc) { this.name = name; this.desc = desc; }
public String getName() { return name; }
public String getDesc() { return desc; }
@Override public String toString() { return "Season{" + "name='" + name + '\'' + ", desc='" + desc + '\'' + '}'; } }
public static void main(String[] args) { System.out.println(Season01.SPRING); }
|
enum常用方法
方法名 |
详细描述 |
valueOf |
将字符串转化为枚举对象,要求字符串必须为已有常量名,否则报异常 |
toString |
Enum类已经重写该方法了,返回的是当前对象名。子类可以重写该方法,用来返回对象的属性信息 |
equals |
类似于二元运算符 == |
getDeclaringClass |
得到枚举常量所属的枚举类型 |
name |
返回当前对象名(常量名),子类不能重写 |
ordinal |
返回当前对象的位置号(默认从0开始) |
compareTo |
比较两个枚举常量,比较的就是位置号 |
clone |
枚举类不能被clone。Enum类实现了一个仅抛出异常的不变clone(),防止子类实现克隆方法。 |
values |
返回当前枚举类中的所有常量 |
String类
说明:
- String 对象用于保存字符串,也就是一组字符序列
- 字符串的字符使用 Unicode 字符编码,一个字符(不区分字母还是汉字)占两个字节大小
- String 类有很多构造器,常用的有:
- String str = new String();
- String str = new String(String original);
- String str = new String(char[] a);
- String str = new String(char[] a, int startIndex, int count);
- String str = new String(byte[] b);
- String 类实现了 Serializable 接口(可以串行化:可以在网络上传输,可以保存到文件)
- String 类实现了 Comparable 接口(String 对象可以比较大小)
- String 是 final 类,不能被其他的类继承
- String 内部实现时:private final char value[]; 存储时本质就是不可变字符数组
声明和创建
1 2 3 4 5 6
| String str;
1. String str = "Hello, world!"; 2. String str = new String("Hello, world!");
|
两种字符串创建方式的区别:
方式一:先从常量池查看是否有”Hello, world!”数据空间,如果有,则直接指向;如果没有,则重新创建然后指向。所以str最终指向的是常量池的空间地址。相当于值传递。
方式二:先在堆中创建空间,里面维护了value属性,指向常量池的”Hello, world!”数据空间。如果常量池没有”Hello, world!”,则重新创建。所以使用这种方法,实际上是创建了两个对象。相当于引用。
String类常用方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77
| 字符串的比较: matches 判断字符串与指定正则表达式是否相匹配,如: String a = "Hello"; String re = ".*?"; System.out.println(a.matches(re)); equals 判断字符串在堆中是否相等 compareTo 比较两个字符串的大小 前面的参数大返回1 后边的参数大则返回-1 相等返回0 regionMatches 比较两个字符串的特定区域是否相等 参数:字符串1.regionMathes((是否忽略大小写boolean,)串1起始下标,字符串2,串2起始下标,比较长度); startsWith 检测字符串是否以指定前缀开始 endsWith 检测字符串是否以指定后缀结束 equalsIgnoreCase 忽略大小写 compareToIgnoreCase 忽略大小写 获取字符串 length() charAt() 用于返回指定索引的字符 str1 = str1.concat(str2); 将str2连接到str1上,并返回连接后的字符串 substring 返回指定字符串的子串 参数:str1.substring(起始下标,(终止下标)); 在原字符串的基础上创建新字符串(不改变原字符串),返回String类型 toLowerCase 将字符串变为小写 toUpperCase 将字符串变为大写 trim 删除字符串的头尾空白符 replace 替换原字符串中的特定字符/字符串 参数:str1.replace(old, new); replaceFirst 替换原字符串第一个匹配给定正则表达式的子字符串 参数:str1.replaceFirst(正则表达式,替换的串); 匹配失败返回原字符串 replaceAll 替换原字符串所有匹配给定正则表达式的子字符串 split 根据给定的正则表达式拆分字符串,返回字符串数组类型 参数:str1.split(正则表达式(,要拆分的份数)); 从前往后拆分 找出某个字符串或者字串(以下两个方法方法重载方法较多) indexOf 参数:str1.indexOf(char/String(,fromIndex)); 返回指定字符/字符串(从fromIndex位置开始)在母串第一次出现处的索引,如果没有,返回-1 lastIndexOf 返回指定字符/字符串在母串最后一次出现处的索引,如果没有,返回-1。如果有fromIndex参数,则从此位置反向索引 字符串与数组之间的转化 串转化为数组 getBytes((String charsetName)); 使用特定的字符集将字符串编码为byte序列,并将结果存储到一个新的byte数组中。如果不写参数,会使用平台默认的字符集 toCharArray 直接返回字符串转换而成的字符数组 参数:str1.toCharArray(); getChars 参数:str1.getChars(要复制的第一个字符的下标,要复制的最后一个字符的下标,目标字符数组,目标字符数组的起始下标); 没有返回值,但会抛出IndexOutOfBoundsException异常 数字转化为串 new String(char[]) 将字符数组转换为字符串并返回 String.valueOf(Object o); 将传进去的int/long/float/double/Object/char/char[]/boolean类型转换为String类型并返回 格式化字符串 format 如:System.out.format("%s", str1);等同于 System.out.printf("%s", str1);
|
StringBuilder 和 StringBuffer 类
String 中的内容是不可变的,当需要对字符串中的内容做修改时,应使用StringBuilder和StringBuffer类。(上述方法提到的修改String内容的方法实际上是创建了新对象,使用StringBuilder和StringBuffer修改时不会产生新对象)
区别
区别:StringBuilder 类是在 Java5 之后才出现的。StringBuilder 的方法是线程不安全的(不能同步访问),但是它的效率更高。
常用方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
| StringBuilder类/StringBuffer类 append 将指定字符插入到原字符的末尾 insert 参数:str1.insert(offset, str); 将字符串str插入到原字符串str1的下标为offset后的位置 delete 参数:str1.delete(start, end); 删除str1从start到end的内容(前闭后开) reverse 将字符串反转 replace 参数:str1.replace(start, end, str); 用str替换str1中从start到end之间的内容(前闭后开) setCharAt 参数:str1.setCharAt(index, char); 将下标为index的内容更改为char 几个常见方法 toString 转为字符串 capacity 返回当前容量 ensureCapacity(int minimumCapacity) 确保容量至少等于指定的最小值 charAt 返回指定下标元素 length() 返回字符串长度 setLength 设置字符序列长度 substring 参数:str1.substring(start(, end)); 返回从start到end之间的内容(end可有可无) trimToSize 将动态数组的容量调整为数组的个数
|
String, StringBuilder, StringBuffer 对比
- String 不可变序列,效率低,但是复用率高,适合在不对字符串修改时使用
- StringBuffer 可变序列,效率较高,但是线程安全,多线程操作时是首选
- StringBuilder 可变序列,效率最高,但是线程不安全,只能在单线程程序中使用
日期和时间
Calendar 类说明:
- Calendar 是一个抽象类,并且构造器是 private
- 可以通过 getInstance() 来获取实例
- Calendar 提供了大量的方法和字段给程序员
- Calendar 没有提供对应的格式化的类,因此需要程序员自己组合来输出
- 如果要按照 24 小时进制来获取时间,Calendar.HOUR ==改成==> Calendar.HOUR_OF_DAY
1 2 3 4 5 6 7 8 9
| Calendar c = Calendar.getInstance();
System.out.println("年" + c.get(Calendar.YEAR)); c.get(Calendar.MONTH)+1; c.get(Calendar.DAY_OF_MONTH); c.get(Calendar.HOUR); c.get(Calendar.MINUTE); c.get(Calendar.SECOND);
|
注意:Calendar 返回月份时,默认是从0开始,所以要加1
前两代日期类的不足的分析:
JDK1.0 中包含了一个 java.util.Date 类,但是它的大多数方法已经在 JDK1.1 引入 Calendar 类之后被弃用了。而 Calendar 也存在的问题是:
- 可变性:像日期和时间等这样的类应该是不可变的。
- 偏移性:Date 中的年份是从 1900 开始的,而月份都从 0 开始。
- 格式化:格式化只对 Date 有用,Calendar 则不行。
- 此外,他们也是线程不安全的;不能处理闰秒等(每隔2天,多出1秒)。
第三代日期常用方法(JDK8 加入)
- LocalDate (日期==年月日)
- LocalTime (时间==时分秒)
- LocalDateTime (日期时间==年月日时分秒)
1 2 3 4 5 6 7 8 9
| LocalDateTime ldt = LocalDateTime.now(); System.out.println(ldt); System.out.println(ldt.getYear()); System.out.println(ldt.getMonth()); System.out.println(ldt.getMonthValue()); System.out.println(ldt.getDayOfMonth()); System.out.println(ldt.getHour()); System.out.println(ldt.getMinute()); System.out.println(ldt.getSecond());
|
可以使用 DateTimeFormatter 类对日期进行格式化,代码如下:
1 2 3 4 5
| LocalDateTime ldt = LocalDateTime.now();
DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"); String format = dateTimeFormatter.format(ldt); System.out.println(format);
|
其他
Instant 时间戳:
1 2 3 4 5 6 7 8 9
| Instant now = Instant.now(); System.out.println(now);
Date date = Date.from(now);
Instant instant = date.toInstant();
|
还有一系列的 plus 和 minus 方法可以对日期进行加减操作
1 2 3 4 5 6 7
| LocalDateTime localDateTime = ldt.plusDays(890); System.out.println("890天后 = " + dateTimeFormatter.format(localDateTime));
LocalDateTime localDateTime2 = ldt.minusMinutes(3456); System.out.println("3456分钟前 = " + dateTimeFormatter.format(localDateTime2));
|
常用包装类
Java 为每一个内置数据类型提供了对应的包装类。所有的包装类(Integer, Long, Byte, Double, Float, Short)都是抽象类 Number 的子类。
对应关系如下:
包装类 |
基本数据类型 |
Boolean |
boolean |
Byte |
byte |
Short |
short |
Integer |
int |
Long |
long |
Character |
char |
Float |
float |
Double |
double |
继承关系如下:

从内置类型到包装类叫做装箱,从包装类对象到内置类型叫做拆箱。
只有变成了包装类才能使用类中的方法,而且一般编译器会自动进行装箱、拆箱的过程。
除 Character 外,字符串都可以通过 parseXXX(String str) 的方法转化为基本数据类型
Math数学类
Math 类常用方法(Math 类的方法都为 static 形式,可以直接使用):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
| 1. 三角函数方法 double sin(double radians) double cos(double radians) double tan(double radians) double toRadians(double degrees) double toDegrees(double radians) double asin(double a) double acos(double a) double atan(double a) 2. 指数函数方法 double exp(double x) e的x次方 double log(double x) ln(x) double log10(double x) lg(x) double pow(double a,double b) a的b次方 double sqrt(double x) x的平方根 3. 服务方法 取整方法 double ceil(double x) //向上取整 double floor(double x) //向下取整 double rint(double x) //向最近的取整 int round(float x) //四舍五入 long round(double x) //四舍五入 min, max, abs方法 random方法 4. double型常量:Math.PI(圆周率) Math.E(自然对数的底数)
|
System 类
常用方法:
- exit 退出当前程序
- arrayCopy 复制数组元素,比较适合底层调用。一般使用 Arrays.copyOf 完成复制数组。
1 2 3
| int[] source = {1, 2, 3}; int destination = new int[3]; System.arrayCopy(source, 0, destination, 0, 3);
|
- currentTimeMillens 返回当前时间距离 1970-1-1 的毫秒数
- gc 运行垃圾回收机制 System.gc();