java常用类

1.String类

1).什么是字符串?

字符串是由多个字符组成的一串数据(字符序列),字符串可以看成是字符数组.

2).String类的概述

String 类代表字符串。Java 程序中的所有字符串字面值(如 “abc” )都作为此类的实例实现。
字符串是常量;它们的值在创建之后不能更改。字符串缓冲区支持可变的字符串。因为 String 对象是不可变的,所以可以共享。

3).字符串常量池

我们知道字符串的分配和其他对象分配一样,是需要消耗高昂的时间和空间的,而且字符串我们使用的非常多。JVM为了提高性能和减少内存的开销,在实例化字符串的时候进行了一些优化:使用字符串常量池。每当我们创建字符串常量时,JVM会首先检查字符串常量池,如果该字符串已经存在常量池中,那么就直接返回常量池中的实例引用。如果字符串不存在常量池中,就会实例化该字符串并且将其放到常量池中。

4).String的常见构造方法

public String():空构造,初始化一个新创建的 String 对象,使其表示一个空字符序列
public String(byte[] bytes):把字节数组转成字符串      
public String(byte[] bytes,int index,int length):把字节数组的一部分转成字符串(index:表示的是从第几个索引开始, length表示的是长度)
public String(char[] value):把字符数组转成字符串
public String(char[] value,int index,int count):把字符数组的一部分转成字符串
public String(String original):把字符串常量值转成字符串
5).String类常用方法
public boolean equals(Object obj):                              比较字符串的内容是否相同,区分大小写
public boolean equalsIgnoreCase(String str):              比较字符串的内容是否相同,忽略大小写
public boolean contains(String str):                            判断字符串中是否包含传递进来的字符串
public boolean startsWith(String str):                         判断字符串是否以传递进来的字符串开头
public boolean endsWith(String str):                          判断字符串是否以传递进来的字符串结尾
public boolean isEmpty():                                           判断字符串的内容是否为空。
public int length():                                                      获取字符串的长度。
public char charAt(int index):                                      获取指定索引位置的字符
public int indexOf(int ch):                                            返回指定字符在此字符串中第一次出现处的索引。
public int indexOf(String str):                                       返回指定字符串在此字符串中第一次出现处的索引。
public int indexOf(int ch,int fromIndex):                       返回指定字符在此字符串中从指定位置后第一次出现处的索引。
public int indexOf(String str,int fromIndex):                 返回指定字符串在此字符串中从指定位置后第一次出现处的索引。
public String substring(int start):                                 从指定位置开始截取字符串,默认到末尾。
public String substring(int start,int end):                     从指定位置开始到指定位置结束截取字符串。
public String replace(char old,char new)                      将指定字符进行替换
public String replace(String old,String new)                 将指定字符串进行替换
public String trim()                                                     去除两端空格
注意:“String对象一旦被创建就是固定不变的了,对String对象的任何改变都不影响到原对象,相关的任何change操作都会生成新的对象”。

5).String深度理解


/**
 * 采用字面值的方式赋值
 */
public void test1(){
    String str1="aaa";
    String str2="aaa";
    System.out.println("===========test1============");
    System.out.println(str1==str2);//true 可以看出str1跟str2是指向同一个对象
}

分析:当执行String str1="aaa"时,JVM首先会去字符串池中查找是否存在"aaa"这个对象,如果不存在,则在字符串池中创建"aaa"这个对象,然后将池中"aaa"这个对象的引用地址返回给字符串常量str1,这样str1会指向池中"aaa"这个字符串对象;如果存在,则不创建任何对象,直接将池中"aaa"这个对象的地址返回,赋给字符串常量。当创建字符串对象str2时,字符串池中已经存在"aaa"这个对象,直接把对象"aaa"的引用地址返回给str2,这样str2指向了池中"aaa"这个对象,也就是说str1和str2指向了同一个对象,因此语句System.out.println(str1 == str2)输出:true。


/**
 * 采用new关键字新建一个字符串对象
 */
public void test2(){
    String str3=new String("aaa");
    String str4=new String("aaa");
    System.out.println("===========test2============");
    System.out.println(str3==str4);//false 可以看出用new的方式是生成不同的对象
}

分析: 采用new关键字新建一个字符串对象时,JVM首先在字符串池中查找有没有"aaa"这个字符串对象,如果有,则不在池中再去创建"aaa"这个对象了,直接在堆中创建一个"aaa"字符串对象,然后将堆中的这个"aaa"对象的地址返回赋给引用str3,这样,str3就指向了堆中创建的这个"aaa"字符串对象;如果没有,则首先在字符串池中创建一个"aaa"字符串对象,然后再在堆中创建一个"aaa"字符串对象,然后将堆中这个"aaa"字符串对象的地址返回赋给str3引用,这样,str3指向了堆中创建的这个"aaa"字符串对象。当执行String str4=new String(“aaa”)时, 因为采用new关键字创建对象时,每次new出来的都是一个新的对象,也即是说引用str3和str4指向的是两个不同的对象,因此语句System.out.println(str3 == str4)输出:false。




/**
 * 编译期确定
 */
public void test3(){
    String s0="helloworld";
    String s1="helloworld";
    String s2="hello"+"world";
    System.out.println("===========test3============");
    System.out.println(s0==s1); //true 可以看出s0跟s1是指向同一个对象
    System.out.println(s0==s2); //true 可以看出s0跟s2是指向同一个对象
}

分析:因为例子中的s0和s1中的"helloworld”都是字符串常量,它们在编译期就被确定了,它们都是字符串常量。

 * 编译期无法确定
 */
public void test4(){
    String s0="helloworld";
    String s1=new String("helloworld");
    String s2="hello" + new String("world");
    System.out.println("===========test4============");
    System.out.println( s0==s1 ); //false 
    System.out.println( s0==s2 ); //false
    System.out.println( s1==s2 ); //false
}

分析:用new String() 创建的字符串不是常量,不能在编译期就确定,所以new String() 创建的字符串不放入常量池中,它们有自己的地址空间。s0还是常量池中"helloworld”的引用,s1因为无法在编译期确定,所以是运行时创建的新对象"helloworld”的引用,s2因为有后半部分new String(”world”)所以也无法在编译期确定,所以也是一个新创建对象"helloworld”的引用。





/**
 * 继续-编译期无法确定
 */
public void test5(){
    String str1="abc";  
    String str2="def";  
    String str3=str1+str2;
    System.out.println("===========test5============");
    System.out.println(str3=="abcdef"); //false
}

分析:因为str3指向堆中的"abcdef"对象,而"abcdef"是字符串池中的对象,所以结果为false。JVM对String str=“abc"对象放在常量池中是在编译时做的,而String str3=str1+str2是在运行时刻才能知道的。new对象也是在运行时才做的。而这段代码总共创建了5个对象,字符串池中两个、堆中三个。+运算符会在堆中建立来两个String对象,这两个对象的值分别是"abc"和"def”,也就是说从字符串池中复制这两个值,然后在堆中创建两个对象,然后再建立对象str3,然后将"abcdef"的堆地址赋给str3。





/**
 * 编译期优化
 */
public void test6(){
    String s0 = "a1";
    String s1 = "a" + 1;
    System.out.println("===========test6============");
    System.out.println((s0 == s1)); //result = true 
    String s2 = "atrue";
    String s3= "a" + "true";
    System.out.println((s2 == s3)); //result = true 
    String s4 = "a3.4";
    String s5 = "a" + 3.4;
    System.out.println((s4 == s5)); //result = true
}

分析:在程序编译期,JVM就将常量字符串的"+“连接优化为连接后的值,拿"a” + 1来说,经编译器优化后在class中就已经是a1。在编译期其字符串常量的值就确定下来,故上面程序最终的结果都为true。





/**
 * 编译期无法确定
 */
public void test7(){
    String s0 = "ab";
    String s1 = "b";
    String s2 = "a" + s1;
    System.out.println("===========test7============");
    System.out.println((s0 == s2)); //result = false
}

分析:JVM对于字符串引用,由于在字符串的"+“连接中,有字符串引用存在,而引用的值在程序编译期是无法确定的,即"a” + s1无法被编译器优化,只有在程序运行期来动态分配并将连接后的新地址赋给s2。所以上面程序的结果也就为false。





/**
 * 比较字符串常量的"+"和字符串引用的"+"的区别
 */
public void test8(){
    String test="javalanguagespecification";
    String str="java";
    String str1="language";
    String str2="specification";
    System.out.println("===========test8============");
    System.out.println(test == "java" + "language" + "specification");//true
    System.out.println(test == str + str1 + str2);//false
}

分析:为什么出现上面的结果呢?这是因为,字符串字面量拼接操作是在Java编译器编译期间就执行了,也就是说编译器编译时,直接把"java"、“language"和"specification"这三个字面量进行”+“操作得到一个"javalanguagespecification” 常量,并且直接将这个常量放入字符串池中,这样做实际上是一种优化,将3个字面量合成一个,避免了创建多余的字符串对象。而字符串引用的"+“运算是在Java运行期间执行的,即str + str2 + str3在程序执行期间才会进行计算,它会在堆内存中重新创建一个拼接后的字符串对象。总结来说就是:字面量”+“拼接是在编译期间进行的,拼接后的字符串存放在字符串池中;而字符串引用的”+“拼接运算实在运行时进行的,新创建的字符串存放在堆中。对于直接相加字符串,效率很高,因为在编译器便确定了它的值,也就是说形如"I”+“love”+“java”; 的字符串相加,在编译期间便被优化成了"Ilovejava"。对于间接相加(即包含字符串引用),形如s1+s2+s3; 效率要比直接相加低,因为在编译器不会对引用变量进行优化。
1:记录一个字符在字符串中出现的次数



//输入一个字符串,并再输入一个字符,输出该字符出现的次数
public static void main(String[] args) {
        Scanner s=new Scanner(System.in);
        System.out.println("输入1:");
        String str1=s.nextLine();
        System.out.println("输入2:");
        char str2=s.nextLine().charAt(0);
        char[] chars = str1.toCharArray();
        int count=0;
        for(char c:chars){
            if(c==str2){
                count++;
            }
        }
        System.out.println("字符"+str2+"出现了"+count+"次");
}
2:记录一个子串在整串中出现的次数


//输入一个字符串,并再输入一个字符串,输出该字符串出现的次数
public static void main(String[] args) {
    Scanner s=new Scanner(System.in);
    System.out.println("输入1:");
    String str1=s.nextLine();
    System.out.println("输入2:");
    String str2=s.nextLine();
    int count =0;
    find(str1,str2,count);
}
public static void find(String str1,String str2,int count){
        int index=str1.indexOf(str2);
        if(index>=0){
            count++;
            //如果能在总字符串里找到子字符串
            //就进行截取字符串,从查到索引位置起数子字符串长度个开始截取,到最后结束
            String news = str1.substring(index + str2.length(), str1.length());
            find(news,str2,count);
        }else {
            System.out.println(count);
        }
 
    }

2.StringBuffer类
1).StringBuffer类概述
StringBuffer是线程安全的可变字符序列.我们如果对字符串进行拼接操作,每次拼接,都会构建一个新的String对象,既耗时,又浪费空间。而StringBuffer就可以解决这个问题.
2).StringBuffer构造方法

public StringBuffer():                                    无参构造方法,构建一个不带字符的字符串缓冲区,大小为16个字符
public StringBuffer(int capacity):                  指定容量的字符串缓冲区对象
public StringBuffer(String str):                     指定字符串内容的字符串缓冲区对象
3).StringBuffer常用方法
public int capacity():                                                   返回当前容量的理论值
public int length():                                                        返回长度(字符数)。 实际值
public StringBuffer append(String str):                          可以把任意类型数据添加到字符串缓冲区里面,并返回字符串缓冲区本身
public StringBuffer insert(int offset,String str):               在指定位置把任意类型的数据插入到字符串缓冲区里面,并返回字符串缓冲区本身
public StringBuffer deleteCharAt(int index):                   删除指定位置的字符并返回本身
public StringBuffer delete(int start,int end):                   删除从指定位置开始指定位置结束的内容,并返回本身
public StringBuffer replace(int start,int end,String str):   从start开始到end用str替换
public StringBuffer reverse():                                         字符串反转
public String substring(int start):                                   从指定位置截取到末尾(返回值类型不再是StringBuffer本身)
public String substring(int start,int end):                       截取从指定位置开始到结束位置,包括开始位置,不包括结束位置(返回值类型不再是StringBuffer本身)

4).String和StringBuffer互相转化

A::String --> StringBuffer
a:通过构造方法
b:通过append()方法
B:StringBuffer -- > String
a: 使用substring方法
b:通过构造方法
c:通过toString()方法
3.StringBuilder
与StringBuffer操作一致,效率更快,但是线程不安全,

4.包装类
1).什么是包装类?
Java是一个面向对象的编程语言,但是Java中的八种基本数据类型却是不面向对象的,为了使用方便和解决这个不足,在设计类时为每个基本数据类型设计了一个对应的类进行代表,这样八种基本数据类型对应的类统称为包装类(Wrapper Class),包装类均位于java.lang包。
2).基本数据的包装类

3).包装类的实际使用
①基本数据和包装类的转换



int n=5;
Integer n1=new Integer(n);
System.out.println("int类型转换为integer类:"+n1);
Integer i=new Integer(50);
int i1 = i.intValue();
System.out.println("integer类转换为int类型:"+i1);

②数值字符串和整型互转



//parseInt方法: 数字字符串类型转成int类型
String ss="123";
int ii = Integer.parseInt(ss);
System.out.println("字符类型转成整型:"+ii);
//toString方法:int类型转成数字字符串类型
int ii2=123;
String ss2 = Integer.toString(ii2);
System.out.println("int类型转成数字字符串类型:"+ss);

4).拆箱与装箱
基本数据类型和对应的包装类可以相互转换,由基本数据类型向包装类转换称为装箱,反之为拆箱!
5.Date类与Calendar类
1).Date类
使用Date类的无参数构造方法创建的对象可以获取本地当前时间。
Date date=new Date();
时间戳:指格林威治时间1970年01月01日00时00分00秒(北京时间1970年01月01日08时00分00秒)起至现在的总毫秒数。
获取时间戳:

date.getTime();
System.currentTimeMillis();
SimpleDateFormat(格式化日期):日期和时间格式由 日期和时间模式字符串 指定。在 日期和时间模式字符串 中,未加引号的字母 ‘A’ 到 ‘Z’ 和 ‘a’ 到 ‘z’ 被解释为模式字母,用来表示日期或时间字符串元素。

也就是说,这些A——Z,a——z这些字母(不被单引号包围的)会被特殊处理替换为对应的日期时间,其他的字符串还是原样输出。
日期和时间模式:
yyyy:年
MM:月
dd:日
hh:1~12小时制(1-12)
HH:24小时制(0-23)
mm:分
ss:秒
S:毫秒
E:星期几
D:一年中的第几天
a:上下午标识
日期类转字符串:


Date ss = new Date();
System.out.println("一般日期输出:" + ss);
System.out.println("时间戳:" + ss.getTime());
SimpleDateFormat  format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");//将目标格式传入构造方法
String time = format.format(ss.getTime());

字符串转日期类:


String s = "2019-03-15";
SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
Date date = format.parse(s);

2).Calendar类
在实际项目当中,我们经常会涉及到对时间的处理,例如登陆网站,我们会看到网站首页显示XXX,欢迎您!今天是XXXX年。。。。某些网站会记录下用户登陆的时间,比如银行的一些网站,仅需要获取当前时间的某部分,比如年份月份邓,
对于这些经常需要处理的问题,Java中提供了Calendar这个专门用于对日期进行操作的类(Date类在jdk1.1中也行,但后来都被淘汰掉了)。
首先我们来看Calendar的声明:
public abstract class Calendar extends Object implements Serializable, Cloneable, Comparable
该类被abstract所修饰,说明不能通过new的方式来获得实例,对此,Calendar提供了一个类方法getInstance,以获得此类型的一个通用的对象,getInstance方法返回一个Calendar对象(该对象为Calendar的子类对象),

其日历字段已由当前日期和时间初始化:
Calendar rightNow = Calendar.getInstance();
获取时间:


// 获取年
 int year = calendar.get(Calendar.YEAR);
 // 获取月,这里需要需要月份的范围为0~11,因此获取月份的时候需要+1才是当前月份值
 int month = calendar.get(Calendar.MONTH) + 1;
// 获取日
 int day = calendar.get(Calendar.DAY_OF_MONTH);
// 获取时
int hour = calendar.get(Calendar.HOUR);
// int hour = calendar.get(Calendar.HOUR_OF_DAY);// 24小时表示
 // 获取分
int minute = calendar.get(Calendar.MINUTE);
// 获取秒
int second = calendar.get(Calendar.SECOND);
设置时间:


// 时
calendar.set(Calendar.HOUR_OF_DAY, 0);
// 分
calendar.set(Calendar.MINUTE, 0);
// 秒
calendar.set(Calendar.SECOND, 0);
// 毫秒
calendar.set(Calendar.MILLISECOND, 0);
Calendar和Data转化:


//Calendar转化为Data
Calendar calendar = Calendar.getInstance();//日历类的实例化
calendar.set(year, month - 1, day);//设置日历时间,月份必须减一
Date date = calendar.getTime(); // 从一个 Calendar 对象中获取 Date 对象
 
 
//Data转化为Calendar
Date date = new Date();//直接new对象,获取的是当前时间
Calendar calendar = Calendar.getInstance();
calendar.setTime(date);

3:算算自己活了多少天



public static void main(String[] args) {
        //算算自己活了多少天
        Date date=new Date();
        long now=date.getTime();//现在的时间戳
        Calendar c=Calendar.getInstance();
        c.set(2000,2,30);//设置出生时间
        Date date1=c.getTime();//获取出生时间戳
        long birth=date1.getTime();
        System.out.println((now-birth)/1000/60/60/24);
}

案例:求下个月的今天的倒数3天

public static void main(String[] args) {
        Calendar c=Calendar.getInstance();
        c.set(Calendar.MONTH,c.get(Calendar.MONTH)+1);
        c.set(Calendar.DAY_OF_MONTH,c.get(Calendar.DAY_OF_MONTH-3));
}

6.Math类
Math 类包含用于执行基本数学运算的方法,如初等指数、对数、平方根和三角函数。
1).Math类中常用方法

Math类中所有方法都为静态方法.
Math.floor():         向下取整
Math.round():      四舍五入
Math.ceil():          取不小于num的最小整数
Math.abs():         取绝对值
Math.random():  生成[0,1)之间的随机小数
Math.pow(a,b):   a的b次方
Math.sqrt(num): num的平方根
Math.max():        返回参数中的最大值
随机生成[a,b]中的随机整数:(int)(Math.random()*(b-a+1)+a);
2).Math类中的成员变量
Math类中所有成员变量都是静态成员变量.
Math.E:    自然对数的底数e
Math.PI:   圆周率π

7.Scanner类
1).Scanner概述
用于获取用户的键盘输入.
2).Scanner常用方法

hasNextXxx():                          判断下一个是否是某种类型的元素,其中Xxx可以是Int,Double等。
public int nextInt():                  获取一个int类型的值
public String nextLine():           获取一个String类型的值


import java.util.Scanner;
public class Demo01_Scanner {
public static void main(String[] args) {   
//2. 创建键盘录入数据的对象        
Scanner sc = new Scanner(System.in);        
        
//3. 接收数据        
System.out.println("请录入一个整数:");        
int i = sc.nextInt();        
        
//4. 输出数据        
System.out.println("i:"+i);        
}    
}

8.System类
1).概述
System 类中提供了大量的静态方法,可以获取与系统相关的信息或系统级操作。
2).常用方法
currentTimeMillis() :返回以毫秒为单位的当前时间(时间戳)–获取当前系统时间与1970年01月01日00:00点之间的毫秒差值;

import java.util.Date;
public class SystemDemo {
    public static void main(String[] args) {
       //获取当前时间毫秒值
       System.out.println(System.currentTimeMillis()); // 1516090531144
      //计算程序运行时间
       long start = System.currentTimeMillis();
        for (int i = 0; i < 10000; i++) {
            System.out.println(i);
        }
        long end = System.currentTimeMillis();
        System.out.println("共耗时毫秒:" + (end ‐ start));
    }
  
}
arraycopy(Object src, int srcPos, Object dest, int destPos, int length) :将数组中指定的数据拷贝到另一个数组中

5个参数含义为:

import java.util.Arrays;
public class Demo11SystemArrayCopy {
    public static void main(String[] args) {
        int[] src = new int[]{1,2,3,4,5};
        int[] dest = new int[]{6,7,8,9,10};
        System.arraycopy( src, 0, dest, 0, 3);
        /*代码运行后:两个数组中的元素发生了变化
         src数组元素[1,2,3,4,5]
         dest数组元素[1,2,3,9,10]
        */
    }
}
exit(int status)   终止当前正在运行的 Java 虚拟机;
int status:状态码,给JVM看,0:正常终止,其他数字:异常终止

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值