2020-05-12

异常处理和String类

1、异常处理

1.1 Exception 的两种处理方式概述

这两种方式就是Java中处理异常的方式

    【捕获】 有能力处理你就捕获,自己的问题你就捕获

    【抛出】 没有办法处理,或者不是自己的问题,和自己无关,因别人导致的错误,抛出

1.2 捕捉异常

1.2.1 基本格式

格式:

    try {

        // 有可能出现问题的代码,存在一定隐患的代码

    } catch (异常类型) {

        // 对应当前异常类型的处理方式

        // 【因为技术所限,我们只能sout 或者 printStackTrace 后期我们会使用

        日志log】

    }

package com.qfedu.a_exception;

public class Demo1 {

    public static void main(String[] args) {

        int num1 = 0;

        int num2 = 20;

        int ret = 0;

        /*

        * num2 / num1 是存在一定的隐患的,如果num1保存的数据是0,

        * 这里会出现一个算术异常

        */

        try {

            // 有可能出现异常的代码

            ret = num2 / num1;

        } catch (ArithmeticException e) {

            /*

            * ArithmeticException 算术异常,catch块中捕获对应异常

            * catch大括号内是对应的处理方式,现在只能展示效果

            */

            e.printStackTrace();

        }

        System.out.println(ret);

        /*

        * java.lang.ArithmeticException: / by zero

        * at com.qfedu.a_exception.Demo1.main(Demo1.java:16)

        * 0

        */

    }

}

1.2.2 细节问题和注意事项

    1. 代码中出现异常,JVM会终止代码运行,如果使用try catch捕获处理异常,JVM会认为当前代码中不存在异常,可以继续运行。

    2. 在try大括号内或者catch大括号内都是局部变量,处理操作数据时小心谨慎。

    3. try - catch捕获处理异常,可以处理多种异常情况!!!而且建议异常处理分门别类,对症下药

    4. 代码中存在多种隐患,存在多个异常情况,try - catch捕获有且只能处理第一个出现异常的代码,因为JVM从异常代码开始直接进入异常捕获阶段

    5. Exception作为Java中所有异常的超类,在捕获异常处理时如果直接使用Exception进行捕获处理,无法做到异常对症下药操作。

    6. Exception可以作为try - catch 最后一个,用于处理其他异常捕获之后没有对症方式遗留问题。[不多见]

1.3 跳出异常

1.3.1 基本格式

关键字:

    throw

        在方法内特定条件下抛出指定异常

    throws

        在【方法声明】位置,告知调用者,当前方法有哪些异常抛出

    用于处理非当前方法操作问题,导致出现的异常,一般情况下是用于处理方法运行过程中因为参数传入,参数处理,运算结果导致的问题,抛出异常。

    throw是一个高级的参数合法性判断!!!

/*

* throws 关键字在方法声明位置告知当前方法的调用者,这里存在异常信息               

*/                                                   

/**                                                   

* 测试方法                                               

*                                                     

* @param num1 int类型参数                                 

* @param num2 int类型参数                                 

* @throws ArithmeticException 如果除数为0,当前方法抛出算术异常       

*/                                                   

public static void test(int num1, int num2) throws ArithmeticException {                   

    /*                                                 

    参数合法性判断 之前的方式 low                                 

    if (0 == num2) {                                   

        System.out.println("你个瘪犊子...坑我");             

        System.exit(0);                               

    }                                                 

    */                                                 

    // 参数合法性判断,如果num2 为0, 这里存在隐患                       

    if (0 == num2) {                                   

        /*                                             

        * 存在异常,这里创建一个异常对象抛出,这里构造方法中                   

        * 存在无参数构造方法和有参数构造方法                           

        * 无参数构造方法异常信息为null                           

        * 有参数构造方法可以传入一个String类型数据,异常信息为指定字符串内容       

        */                                           

        throw new ArithmeticException("除数不能为0");       

    }                                                 

    // 如果num2的值为0,num1 / num2 操作是存在隐患的,有问题的           

    int ret = num1 / num2;                             

    System.out.println(ret);                           

}

1.3.2 细节问题和注意事项

    1. 代码如果运行到throw抛出异常,之后的代码不再运行,之后的代码是成为无参触及代码

    2. 代码中存在多种隐患,按照隐含的情况,分门别类处理,不能在同一个条件内抛出两个异常。并且在方法的声明位置,throws之后,不同的异常,使用逗号隔开

    3. 当调用带有异常抛出的方法时,对于方法抛出的异常,有两种处理方式,可以捕获处理,也可以抛出处理。

1.4 抛出处理和捕获处理选择

情况分析:

    询指定路径指定名字的文件,存在的异常处理分析过程。

1.5 异常分类

运行时异常:

    RuntimeException 代码运行过程中出现的异常,没有强制处理的必要性

    ArrayIndexOutOfBoundsException 数组下标越界异常

    NullPointerException 空指针异常

    ArithmeticException 算术异常

    运行时异常不强制要求捕获和抛出!!!

    JVM会处理RuntimeException,也就是告知异常的前因后果!!!

其他异常:

    强制要求处理,不管是捕获处理,还是抛出处理,都需要进行操作。

    如果未处理!!!直接报错!!!

    IDE工具的快速修复

        Eclipse  Ctrl + 1

        IDEA Alt + Enter

1.6 自定义异常

自定义单身狗异常

    PFSP

        private final static Person

    我比较习惯这个顺序 代码中常见的也是这个顺序

自定义异常格式:

    class MyException extends Exception {

        // 无参数构造方法

        public MyException() {}

        // 有参数构造方法,且参数数据类型为String类型

        public MyException(String message) {

        super(message);

    }

}

【注意】

    Eclipse会提示要求完成一个ID号,可以忽略,存在一个警告,不用管。

package com.qfedu.a_exception;

/*

* 忽略黄色警告!!!

*/

/**

* 自定义异常,单身狗异常

*

* @author Anonymous

*

*/

public class SingleDogException extends Exception {

    /**

    * 无参数构造方法

    */

    public SingleDogException() {}

    /**

    * 带有参数的构造方法,需要的参数类型是String类型

    *

    * @param message 异常信息内容

    */

    public SingleDogException(String message) {

        /*

        * 通过super关键字调用父类的参数为String类型构造方法

        */

        super(message);

    }

}

package com.qfedu.a_exception;

public class Demo4 {

    public static void main(String[] args) throws SingleDogException {

        try {

            buyOneFreeOne(false);

        } catch (SingleDogException e) {

            // TODO Auto-generated catch block

           System.out.println("两只黄鹂鸣翠柳,你还是个单身狗");

        }

        buyOneFreeOne(true);

    }

    /**

    * 买一送一方法,如果有女朋友满足要求,如果没有不满足要求

    *

    * @param hasGirlFriend boolean类型数据,判断是否有女朋友

    * @throws SingleDogException SingleDog 单身狗异常

    */

    public static void buyOneFreeOne(boolean hasGirlFriend) throws SingleDogException {

        if (false == hasGirlFriend) { // !hasGirlFriend

            // throw 抛出一个异常对象 SingleDogException 自定义异常类

            throw new SingleDogException("路见不平一声吼,你还没有女朋友");

        }

        System.out.println("3RMB 甜筒 买一送一");

    }

}

1.7 异常处理总结

    1. 异常存在的必要性,代码中使用的数据,大多数来源于用户,用户传入数据是一个非常不可靠的情况!!!存在一定错误意识,反馈机制和处理机制。

    2. 异常处理方式

        捕获

        抛出

        要根据使用情况,操作方式,反馈形式来选择对应的处理方式。

    3. 自定义异常,了解异常的构造,基本上在开发中用到自定义异常的情况不多见。但是要了解关于异常信息保存的方式。

2、String类

2.1 字符串类型概述

又爱又恨!!!

    爱:

        字符串基本上就是数据的保存,传输,处理非常重要的一种手段。

    恨:

        解析过程非常烦人,需要掌握熟记很多方法,同时需要有一定的技巧和灵性

    String字符串类型是Java中引用数据类型,并且String类型是使用final修饰,没有自己的子类。

字符串的存储也是非常个性的一件事情,分两种情况,

    一种是在内存的数据区

    一种是在内存的堆区

字符串是一个常量!!!

    字符串确定之后无法修改!!!

2.2 字符串内存分析和equals方法

package com.qfedu.b_string;

/*

* 字符串常量分析

*/

public class Demo1 {

    public static void main(String[] args) {

        String str1 = "烤羊排";

        String str2 = "烤羊排";

        String str3 = new String("烤羊排");

        String str4 = new String(str1);

        /*

        * tfff

        * == 等于判断是比较两个变量中保存的数据是否一致

        * String str1 str2 str3 str4 都是引用数据类型的变量,也就是==判断比较的是

        * str1 ~ str4 中保存的空间首地址

        */

        System.out.println("str1 == str2 : " + (str1 == str2)); // true

        System.out.println("str2 == str3 : " + (str2 == str3)); // false

        System.out.println("str3 == str4 : " + (str3 == str4)); // false

        System.out.println("str4 == str1 : " + (str4 == str1)); // false

        System.out.println("----------------------------------------");

        /*

        * 字符串如何比较是否一致???

        *

        * Java中规定,字符串比较要求采用equals方法来完成,并且使用的equals方法是String类

        * 重写Object类内的方法,比较方式是比较字符串内容。

        */

        System.out.println("str1.equals(str2) : " + str1.equals(str2)); // true

        System.out.println("str2.equals(str3) : " + str2.equals(str3)); // true

        System.out.println("str3.equals(str4) : " + str3.equals(str4)); // true

        System.out.println("str4.equals(str1) : " + str4.equals(str1)); // true

    }

}

2.3 获取方法

int length();

    获取字符串的长度

char charAt(int index);

    从字符串中获取对应下标位置的字符,(存在下标越界问题)

int indexOf(char ch);

    找出指定字符在当前字符串中的下标位置

    "ABCDEFGABCDEFG"

    查询 'E' ==> result 4

int indexOf(String str);

    找出指定字符串在当前字符串中的下标位置

    "ABCDEFGABCDEFG"

    查询 "DE" ==> result 3

int lastIndexOf(char ch);

    找出指定字符最后一次出现的下标位置

    "ABCDABCD";

    查询 'B' ==> result 5

int lastIndexOf(String str);

    找出指定字符串最后一次出现的下标位置

    "ABCDABCD";

    查询 "CD" ==> result 6

package com.qfedu.b_string;

/*

* 获取方法

*/

public class Demo2 {

    public static void main(String[] args) {

        String str = "ABCDEFGABCDEFG";

        // length方法

        System.out.println("str.length() : " + str.length());

        // charAt方法

        System.out.println("str.charAt(5) : " + str.charAt(5));

        System.out.println("str.charAt(0) : " + str.charAt(0));

        // StringIndexOutOfBoundsException 字符串下标操作越界异常 字符串长度为14

        // 有效下标为0 ~ 13

        // ArrayIndexOutOfBoundsException

        // System.out.println("str.charAt(14) : " + str.charAt(14));

        // indexOf方法

        System.out.println("str.indexOf(\"CD\") : " + str.indexOf("CD"));

        System.out.println("str.indexOf('C') : " + str.indexOf('C'));

        // lastIndexOf方法

        System.out.println("str.lastIndexOf(\"CD\") : " + str.lastIndexOf("CD"));

        System.out.println("str.lastIndexOf('C') : " + str.lastIndexOf('C'));

    }

}

2.4 判断方法

boolean endsWith(String str);

    判断当前字符串是不是指定字符串结尾,如果是返回true,不是返回false

boolean startsWith(String str);

    判断当前字符串是不是指定字符串开始,如果是返回true,不是返回false

boolean isEmpty();

    判断当前字符串是否为空,空字符串是指 "" 双引号什么都没有

boolean contains(String str) 是否包含指定序列 应用:搜索

    判断该指定字符串是否是当前字符串的子字符串。

    当前字符串:

        "ABCDEFG";

    参数字符串:

        "CDE"; ==> result true;

    参数字符串:

        "CE"; ==> result false

       原码是调用String类的indexOf方法,找出指定字符串的下标位置,indexOf方法下标为大于等于0,返回 true,否则返回 false

boolean equals(Object anObject);

    重写 Override Object类内方法,判断两个字符串是否一致。

boolean equalsIgnoreCase(String anotherString);

    忽略大小写是否相等,不考虑英文大小写方式比较两个字符串是否一致。

package com.qfedu.b_string;

/*

* 判断方法

*/

public class Demo3 {

    public static void main(String[] args) {

        String str = "ABCDEFGABCDEFG";

        // endsWith方法

        System.out.println("str.endsWith(\"FG\") : " + str.endsWith("FG"));

        System.out.println("str.endsWith(\"FG\") : " + str.endsWith("GF"));

        // startsWith方法

        System.out.println("str.startsWith(\"AB\") : " + str.startsWith("AB"));

        System.out.println("str.startsWith(\"BA\") : " + str.startsWith("BA"));

        // isEmpty方法

        System.out.println("str.isEmpty() : " + str.isEmpty());

        System.out.println("\"\".isEmpty() : " + "".isEmpty());

        // contains方法

        System.out.println("str.contains(\"ABCD\") : " + str.contains("ABCD"));

        System.out.println("str.contains(\"ACBD\") : " + str.contains("ACBD"));

        // equalsIgnoreCase方法

        System.out.println("ABCDEFG".equalsIgnoreCase("AbcdEfg"));

    }

}

2.5 转换方法

String(char[] value);

    将字符数组转换为字符串

String(char[] value, int offset, int count);

    将字符数组转换为字符串,从指定offset位置开始,计数count

        offset是开始位置

        count是截取个数

    例如:

        char[] arr = {'A', 'B', 'C', 'D', 'E'};

    调用方法参数:

        new String(arr, 2, 3); ==> result "CDE"


static String valueOf(char[] data);

    同理String(char[] value);

    tips: 底层代码是 return new String(data);


static String valueOf(char[] data, int offset, int count);

    同理String(char[] value, int offset, int count);

    tips: 底层代码是 return new String(data, offset, count);

char[] toCharArray();

    将字符串转换为字符数组

    例如:

        "ABCDE";

    返回值:

        {'A', 'B', 'C', 'D', 'E'};

package com.qfedu.b_string;

/*

* 转换方法

*/

public class Demo4 {

    public static void main(String[] args) {

        char[] arr = {'A', 'B', 'C', 'D', 'E', 'F', 'G'};

        String str = new String(arr);

        System.out.println(str);

        String str2 = new String(arr, 3, 3);

        System.out.println(str2);

        String str3 = String.valueOf(arr);

        System.out.println(str3);

        String str4 = String.valueOf(arr, 3, 3);

        System.out.println(str4);

        char[] charArray = "你好,这里是骚磊电台".toCharArray();

        for (int i = 0; i < charArray.length; i++) {

            System.out.println(charArray[i]);

       }

    }

}

2.6 其他方法

String replace(char oldChar, char newChar);

    替换使用newChar字符类型,替换当前字符串内的所有指定字符oldChar

    例如:

        "ABCDEABCDE";

    调用方法:

        "ABCDEABCDE".replace('A', '你');

    返回值结果:

        "你BCDE你BCDE"; 【注】原字符串不变


String[] split(String regex); 【重点】

    【重点】切割,将当前字符串按照指定字符串切割成String类型数组

    例如:

        String str = "你好!他好!大家好!广州好迪";

    调用方法:

        str.split("!");

    返回值结果:

        String[] arr = {"你好", "他好", "大家好", "广州好迪"};

    调用方法:

        str.split("好");

    返回值结果:

        String[] arr = {"你", "!他", "!大家","!广州", "迪"};

String substring(int beginIndex); 【重点】

    从指定beginIndex开始,到字符串结尾截取字符串

    例如:

        String str = "ABCDEFG";

    调用方法:

        str.substring(3);

    返回值结果:

        "DEFG"

String substring(int beginIndex, int endIndex); 【重点】

    从指定beginIndex开始,到endIndex结束,截取字符串

    要头不要尾 beginIndex <= 结果范围 < endIndex [3,5)

    例如:

        String str = "ABCDEFG";

    调用方法:

        str.substring(3, 5);

    返回值结果:

        "DE"


String toUpperCase();

    字符串中所有的英文字母转大写,返回新字符串

String toLowerCase();

    字符串中所有的英文字母转小写,返回新字符串                             

String trim();

    去除字符串两边的空格

package com.qfedu.b_string;

import java.util.Arrays;

/*

* 其他方法

*/

public class Demo5 {

    public static void main(String[] args) {

        String str = "ABCDEFGABCDEFG";

        String replace = str.replace('A', '你');

        System.out.println(str);

        System.out.println(replace);

        String str1 = "你好,他好,大家好,广州好迪";

        String[] split = str1.split(",");

        // Arrays数据工具类的toString方法,数组中的元素会使用, 分割

        System.out.println(Arrays.toString(split));

        for (int i = 0; i < split.length; i++) {

            System.out.println(split[i]);

        }

        String substring = str.substring(5);

        System.out.println(substring);

        String substring2 = str.substring(5, 9);

        System.out.println(substring2);

        System.out.println("abc,,,d浩爷EFG".toUpperCase());

        System.out.println("AB!!!!C浩爷Defg".toLowerCase());

        System.out.println();

        String str2 = "                            fdafdsaf        fedadfs                  ";

        System.out.println(str2);

         System.out.println(str2.trim());

    }

}

你可能感兴趣的:(2020-05-12)