API day05

Api day05

笔记

  • 含有throws方法的类被继承后 子类中重写的规则
    • 可以与超类的方法一样抛出(throws)相同异常
    • 可以仅抛出部分异常
    • 可以不抛出异常
    • 可以抛出超类方法异常的子类型异常
    • 不可抛出其他额外异常(既不是超类中的异常也不是子类型异常)
    • 不可抛出超类方法中异常的超类型异常
/**
 * 子类重写超类含有throws声明异常抛出的方法时,对throws的重写规则
 */
public class ThrowsDemo {

    public void dosome() throws IOException, AWTException{}

}
class SubClass extends ThrowsDemo{

//    public void dosome() throws IOException, AWTException{}

    //允许子类只抛出超类方法异常中的一部分
//    public void dosome() throws IOException{}

    //允许子类抛出超类方法抛出异常的子类型异常 FileNotFoundException extends IOException
//    public void dosome() throws FileNotFoundException {}

    //允许子类不再抛出任何异常
//    public void  dosome(){}

    //不允许子类抛出额外异常(超类中没有且没有任何继承关系的)
//    public void dosome() throws SQLException {} //报错

    //不允许子类抛出超类方法抛出异常的超类型异常 IOException extends Exception AWTException extends Exception
//    public void dosome() throws Exception {} //Exception是IOException 和 AWTException 的超类型 子类只允许继承关系 等于或小于的异常

}

常见的RuntimeException子类

RuntimeException异常是非检查异常,即无需进行try-catch 或者 throws的异常,通常都是可以通过修改bug直接改好的,可避免异常。
除了RuntimeException之外的其它异常如果使用throw 是非检查异常
抛出则要在当前方法上使用throws声明该异常的抛出 即是检查异常 需throws

  • IllegalArgumentException:抛出的异常表面向方向传递了一个不合法或不正确的参数
  • NullPointerException:当应用程序试图在需要对象的地方使用null时,抛出该异常
  • ArrayIndexOutOfBoundsException:当使用的数组下标超出数组允许范围时,抛出该异常
  • ClassCastException:当试图将对象强制转换为不是实例的子类时,抛出该异常
  • NumberFormatException:当应用程序试图将字符串转换成一种数值类型,但该字符串不能转换为合适格式时,抛出该异常
异常中常用的方法
package exception;

/**
 * 异常常见的方法
 */
public class ExceptionApiDemo {
    public static void main(String[] args) {
        System.out.println("程序开始了");

        try {
            String str = "abc";
            System.out.println(Integer.parseInt(str));
        } catch (NumberFormatException e) {
            //异常最常用的方法,用于将当前错误信息输出到控制台
            e.printStackTrace();

            //获取错误消息.记录日志的时候或提示给用户可以使用它
            String message = e.getMessage();
            System.out.println(message);

        }

        System.out.println("程序结束了");
    }
}
自定义异常

自定义异常通常用来定义那些业务上的异常问题
定义自定义异常需要注意以下问题

  • 异常的类名要见名知意
  • 需要继承或者间接继承Exception
  • 提供超类异常提供的所有种类构造器
package test;

public class Person {
    private int age;

    public Person() {

    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) throws IllegalAgeException {
        if (age<0 || age>100){
            throw new IllegalAgeException("年龄不合法"+age);
        }
        this.age = age;
    }
}
class Demo{

    public static void main(String[] args) {
        Person p = new Person();
        System.out.println("开始");
        try {
            p.setAge(112);
        } catch (IllegalAgeException e) {
            e.printStackTrace();
            String line = e.getMessage();
            System.out.println(line);
        }
        System.out.println("结束");
    }
}
package test;

public class IllegalAgeException extends Exception {
    public IllegalAgeException() {
    }

    public IllegalAgeException(String message) {
        super(message);
    }

    public IllegalAgeException(String message, Throwable cause) {
        super(message, cause);
    }

    public IllegalAgeException(Throwable cause) {
        super(cause);
    }

    public IllegalAgeException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
        super(message, cause, enableSuppression, writableStackTrace);
    }
}

总结:

异常处理机制是用来处理那些可能存在的异常,但是无法通过修改逻辑完全规避的场景。

而如果通过修改逻辑可以规避的异常是bug,不应当用异常处理机制在运行期间解决!应当在编码时及时修正

java网络编程

java.net.Socket

Socket(套接字)封装了TCP协议的通讯细节,是的我们使用它可以与服务端建立网络链接,并通过 它获取两个流(一个输入一个输出),然后使用这两个流的读写操作完成与服务端的数据交互

java.net.ServerSocket

ServerSocket运行在服务端,作用有两个:

1:向系统申请服务端口,客户端的Socket就是通过这个端口与服务端建立连接的。

2:监听服务端口,一旦一个客户端通过该端口建立连接则会自动创建一个Socket,并通过该Socket与客户端进行数据交互。

如果我们把Socket比喻为电话,那么ServerSocket相当于是某客服中心的总机。
与服务端建立连接案例:

还有需要优化的点,现在没有学习多线程的知识,所以服务器端无法接收多个客户同时连接服务器,并且我独自再客户端中try()添加了流自动关闭的功能,这样才能让客户端顺利退出,服务器端不报错。只有一个客户端退出,另一个才能连接,否则会直接报错。

  • Server服务器端代码
package socket1;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;

public class Server {

    private ServerSocket serverSocket;

    public Server() {
        try {
            System.out.println("启动服务器。。。");
            serverSocket = new ServerSocket(8088);
            System.out.println("服务器启动完毕!");
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

    public void start(){
        try {
            while (true) {
                System.out.println("等待客户端连接。。。");
                Socket socket = serverSocket.accept();
                System.out.println("有一个客户连接");

                InputStream in = socket.getInputStream();
                InputStreamReader isr = new InputStreamReader(in);
                BufferedReader br = new BufferedReader(isr);
                String message;
                while ((message = br.readLine()) != null) {
                    System.out.println("客户端说:" + message);
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public static void main(String[] args) {
        Server server = new Server();
        server.start();
    }
}
  • Client客户端代码
package socket1;

import java.io.*;
import java.net.Socket;
import java.util.Scanner;

public class Client {

    private Socket socket;

    public Client() {
        try {
            System.out.println("客户端启动。。。");
            socket = new Socket("localhost",8088);
            System.out.println("客户端启动成功!");
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public void start(){
        try (
                OutputStream out = socket.getOutputStream();
                OutputStreamWriter osw = new OutputStreamWriter(out);
                BufferedWriter bw = new BufferedWriter(osw);
                PrintWriter pw = new PrintWriter(bw,true);
                )
        {
            Scanner scan = new Scanner(System.in);
            while (true){
                String line = scan.nextLine();
                if ("exit".equals(line)){
                    System.out.println("退出成功");
                    pw.println("我下线了");
                    break;
                }
                pw.println(line);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public static void main(String[] args){
        Client client = new Client();
        client.start();

    }
}

多线程

线程:一个顺序的单一的程序执行流程就是一个线程。代码一句一句的有先后顺序的执行。
多线程:多个单一顺序执行的流程并发运行。造成"感官上同时运行"的效果。
并发:

多个线程实际运行是走走停停的。线程调度程序会将CPU运行时间划分为若干个时间片段并

尽可能均匀的分配给每个线程,拿到时间片的线程被CPU执行这段时间。当超时后线程调度

程序会再次分配一个时间片段给一个线程使得CPU执行它。如此反复。由于CPU执行时间在

纳秒级别,我们感觉不到切换线程运行的过程。所以微观上走走停停,宏观上感觉一起运行

的现象成为并发运行!

用途:
  • 当出现多个代码片段执行顺序有冲突时,希望它们各干各的时就应当放在不同线程上"同时"运行
  • 一个线程可以运行,但是多个线程可以更快时,可以使用多线程运行
创建线程
方式一:继承Thread并重写run方法

定义一个线程类,重写run方法,在其中定义线程要执行的任务(希望和其他线程并发执行的任务)。

注:启动该线程要调用该线程的start方法,而不是run方法!!!

package test;

public class ThreadDemo {
    public static void main(String[] args) {
        Thread t1 = new Thread1();
        Thread t2 = new Thread2();
        /*
            需要注意,启动线程要调用线程的start方法,而不是直接调用run方法!
         */
        t1.start();
        t2.start();
    }
}
class Thread1 extends Thread{
    public void run(){
        for (int i = 0; i < 10000; i++) {
            System.out.println("今天天气怎么样啊?");
        }
    }
}
class Thread2 extends Thread{
    public void run(){
        for (int i = 0; i < 10000; i++) {
            System.out.println("还不错吧,就是风有些大");
        }
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值