Java基础知识点(反射、注解、JDBC、TCP/UDP/URL)

文章目录

  • 反射
    • 反射的定义
    • class对象
    • 反射的操作
  • 注解
    • 注解的定义
    • 注解的应用
    • 注解的分类
      • 基准注解
      • 元注解
    • 自定义注解
      • 自定义规则
      • 自定义demo
  • JDBC
  • TCP/UDP/URL
    • TCP
    • UDP
    • URL

反射

反射的定义

Java Reflection是Java被视为动态语言的基础啊, 反射机制允许程序在执行期间接入Reflection API获取任何类的内部信息,并能直接操作任意对象的内部属性及方法。

class对象

  1. 类加载完成后,在堆内存中就会残生一个该类的Class对象(一个类只有一个Class对象),Class对象中包含了完整类的结构信息,包括:类型、方法、属性、注解、构造函数、类加载起,父类Class对象等。
  2. 在Object类中有一个方法:public final Class getClass();这个方法被所有子类继承。
  3. Calss本身也是一个类。Class对象只能由系统建立,JVM产生。
  4. 一个类加载到JVM中只会产生一个Class对象,一个Class对象对应的是一个加载到JVM中的一个.class文件。
  5. 每个类的实例都会记得自己是由那个Calss实例是生成的,Object的getClass方法。
  6. 通过Class可以完整的得到一个类的所有被加载的结构。
  • Class的创建
//获得class办法一:通过对象获得
Class clazz1 = person.getClass();
//获得class办法二:通过字符串获得(包名+类名)
Class clazz2 = Class.forName("com.reflection.Student");
//获得class办法三:通过类的静态成员class获得
Class clazz3 = Person.class;
//获得class办法四:只针对内置的基本数据类型
Class clazz4 = Integer.TYPE;
//获得父类类型
Class clazz5 = clazz2.getSuperclass();
  • 常用方法
    在这里插入图片描述

  • 哪些类型可以有Class对象?

  • class:外部类,成员(成员内部类,静态内部类),局部内部类,匿名内部类。

  • interface:接口

  • []:数组

  • enum:枚举

  • annotation:注解@interface

  • primitive type:基本数据类型

  • void

反射的操作

  1. Class对象调用newInstance() 方法创建类的对象,类必须有一个无参数构造器,类的构造器必须有访问权限。
  2. 调用指定的方法,通过Class对象获取到具体的Method,然后执行Method的Object invoke(Object obj, Object[] args)方法就可完成调用,
  3. setAccessible
    Method/Field/Constructor对象都有setAccessible方法,setAccessible的作用是启动或者禁止访问安全检查的开关(也就是可以打开私有属性、方法、构造器等),值分为false和true。

注解

注解的定义

  1. Java注解又称Java标注、元数据,它提供了一种安全的类似注解的机制,用来将任何信息或者元数据(metadata)与程序元素(类、方法、属性等)进行关联。
  2. Java注解是附加在代码中的一些元数据,用于一些工具在编译、进行时进行解释和使用,起到说明配置的功能。

注解的应用

  1. 生成文档,也是Java最早提供的注解功能。
  2. 在编译时进行格式检查,例如:@Override注解放在方法前,如果这个方法并不是覆盖了超类的方法,在编译阶段就能检测出。
  3. 跟踪代码的以来星,实现替代配置文件的功能,比较常见的是Spring2.5开始基于注解开发,减少了配置文件的配置。
  4. 在Java反射中,可以解析并使用注解(Annotation),这也是上3实现的底层原理。

注解的分类

基准注解

基准注解就是Java语言自带的注解,主要有:

  1. @Override:作用在METHOD上,使用在SOURCE(源代码阶段),功能是:检查该方法是否是重写方法,如果发现父类超类并没有该方法,就会编译报错。
  2. @Deprecated:作用在CONSTRUCTOR, FIELD, LOCAL_VARIABLE, METHOD, PACKAGE, PARAMETER, TYPE上,使用在RUNTIME阶段,功能是:标记果实方法,如果使用该方法,会编译警告。
  3. @SuppressWarnings:作用在TYPE, FIELD, METHOD, PARAMETER, CONSTRUCTOR, LOCAL_VARIABLE上,使用在SOURCE阶段,功能是:提示编译器去忽略解释中的声明警告。
    在这里插入图片描述
  4. @FunctionalInterface:作用在TYPE上,使用在RUNTIME阶段,功能是:Java8支持,表示一个匿名函数或者函数式接口。

元注解

  1. @Target: 用来定义注解的使用范围,即描述注解可以使用在那些地方,该注解包含9个值,是ElmentType枚举类的枚举类型:
  • TYPE:应用于类、结构、注解类型、枚举上
  • CONSTRUCTOR: 应用于构造函数上
  • PARAMETER: 应用于方法的参数上
  • FIELD: 应用于字段属性上
  • METHOD: 应用于方法上
  • PACKAGE: 应用于包
  • LOCAL_VARIABLE: 应用于局部变量上
  • TYPE_PARAMETER: Java8新增,应用于类型变量
  • TYPE_USE: Java8新增,应用在任何使用类型语句中
  1. @Retention:用来定义该注解可以在哪一个阶段可用,该注解包含3个值,是RententionPolicy枚举类的枚举类型:
  • SOURCE:源代码阶段,编译时被丢弃,不包含在class文件冲,
  • CLASS(默认值):class文件阶段,JVM加载时被丢弃,包含在class文件中,
  • RUNTIME: 运行时阶段,由JVM加载,包含在class文件中,在运行时可以获取到。
  1. @Documented: 生成文档信息时候保留注解,对类起说名作用,该注解将会包含在javadoc中.
  2. @Inherited: 说明子类可以继承父类中的该注解.
  3. @Repeatable:表示允许统一程序元素可以多次使用相同的注解。
//在使用时候,需要同时提供一个容器注解来封装可以重复注解的多个实例:

@Repeatable(Roles.class)
public @interface Role {
    String value();
}
 
// 容器注解
public @interface Roles {
    Role[] value();
}
使用该注解:
@Role("admin")
@Role("supervisor")
public class MyClass {
    // ...
}

自定义注解

自定义规则

  1. 使用@interface自定义注解,使用时激动继承了java.lang.annotation.Annotation接口。
  2. 具体规则:
  • @interface 中每一个方法实际上是声明了一个配置参数,方法的名称就是参数的名称,返回值类型就是蚕食的类型(返回值类型只能是基本类型、Class、String、enum).
  • 通过default来声明蚕食的默认值。
  • 如果只能由一个参数成员,一般参数名为value。
  • 注解元素必须要有值,自定义注解元素时,经常使用空字符串、0作为默认值

自定义demo

自定义注解类:

package com.xxliao.annotation;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

/**
 * @author xxliao
 * @description: 字符初始化
 * @date 2023/11/16$ 1:16$
 */

@Target(value = {ElementType.METHOD,ElementType.FIELD,ElementType.CONSTRUCTOR})// 可在字段、方法上使用
@Retention(value = RetentionPolicy.RUNTIME) // 运行时
public @interface Init {

    String value() default "";

}

实体类:

package com.xxliao.annotation;

/**
 * @author xxliao
 * @description: 用户实体类
 * @date 2024/6/1 15:25
 */

public class User {

    private String name;

    @Init("xxliao")
    public void setName(String name) {
        this.name = name;
    }
    
    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                '}';
    }
}

实体工厂类:

package com.xxliao.annotation;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.List;

/**
 * @author xxliao
 * @description: 用户对象工厂 用来创建用户对象 添加了读取自定义注解 赋默认值的功能
 * @date 2024/6/1 15:27
 */
public class UserFactory {

    private static boolean IS_DEFAULT_VALUE;

    private static Init INIT;

    private static Method METHOD;

    static{
        // 获取User类中所有的方法(getDeclaredMethods也行)
        Method[] methods = User.class.getDeclaredMethods();
        for (Method method : methods) {
            // 如果一个注解指定注解类型是存在于此元素上此方法返回true,否则返回false
            //参数 -- 对应于注解类型的Class对象
            if (method.isAnnotationPresent(Init.class)) {
                //此方法返回该元素的注解在此元素的指定注释类型(如果存在),
                IS_DEFAULT_VALUE  = true;
                INIT =  method.getAnnotation(Init.class);
                METHOD = method;
                break;
            }
        }
    }

    /**
     * @description  创建对象
     * @author  xxliao
     * @date  2024/6/1 15:29
     */
    public static User newInstance()  {
        User instance = new User();
        if(IS_DEFAULT_VALUE) {
            try {
                METHOD.invoke(instance,INIT.value());
            } catch (IllegalAccessException e) {
                throw new RuntimeException(e);
            } catch (InvocationTargetException e) {
                throw new RuntimeException(e);
            }
        }
        return instance;
    }
}

测试类:

package com.xxliao.annotation;

/**
 * @author xxliao
 * @description: 自定义注解 测试客户端
 * @date 2023/11/16$ 1:37$
 */

public class TestClient {

    public static void main(String[] args) {
       User user = UserFactory.newInstance();
       System.out.println(user);
    }
}

演示结果:
在这里插入图片描述

JDBC

//JDBC使用步骤
// 1.加载驱动
Class.forName("com.mysql.jdbc.Driver");
// 2.连接数据库,代表数据库
Connection connection = DriverManager.getConnection(url, username,password);
// 3.向数据库发送SQL的对象Statement,PreparedStatement : CRUD
Statement statement = connection.createStatement();
// 4.编写SQL
String sql = "select * from users";
// 5.执行查询SQL,返回一个 ResultSet : 结果集
ResultSet rs = statement.executeQuery(sql);
while (rs.next()){
System.out.println("id="+rs.getObject("id"));
System.out.println("name="+rs.getObject("name"));
System.out.println("password="+rs.getObject("password"));
System.out.println("email="+rs.getObject("email"));
System.out.println("birthday="+rs.getObject("birthday"));
}
// 6.关闭连接,释放资源(一定要做) 先开后关
rs.close();
statement.close();
connection.close();

TCP/UDP/URL

TCP

server端:

package com.xxliao.tcp;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.ServerSocket;
import java.net.Socket;

/**
 * @author xxliao
 * @description: TCP 服务端
 * @date 2023/11/19$ 12:47$
 */

public class TcpServer {
    public static void main(String[] args) {
        ServerSocket serverSocket = null;
        Socket accept = null;
        InputStream is = null;
        ByteArrayOutputStream baos = null;
        try {
            //1. 开放服务器端口,创建ServerSocket
            serverSocket = new ServerSocket(8899);
            //2. 等待客户端的连接
            accept = serverSocket.accept();
            //3. 读入客户端的消息,
            is = accept.getInputStream();
            /*
            回忆之前的IO流方案,弊端:存在中文,可能存在乱码。
            byte[] buffer = new byte[1024];
            int len;
            while ((len=is.read(buffer))!=-1){
            String str = new String(buffer,0,len);
            System.out.println(str);
            }
            **/
            baos = new ByteArrayOutputStream();
            byte[] buffer = new byte[1024];
            int len;
            while ((len=is.read(buffer))!=-1){
                baos.write(buffer,0,len);
            }
            System.out.println(baos.toString());
            System.out.println(
                    "数据来源地址:"+accept.getInetAddress().getHostName());
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            //4. 关闭资源
            try {
                if (baos!=null){
                    baos.close();
                }
                if (is!=null){
                    is.close();
                }
                if (accept!=null){
                    accept.close();
                }
                if (serverSocket!=null){
                    serverSocket.close();
                }
            }catch (Exception e){
                e.printStackTrace();
            }
        }
    }
}

client端:

package com.xxliao.tcp;

import java.io.IOException;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;

/**
 * @author xxliao
 * @description: TCP演示
 * @date 2023/11/19$ 12:45$
 */

public class TcpClient {
    public static void main(String[] args) {
        Socket socket = null;
        OutputStream os = null;
        try {
            //1. 连接服务器的地址
            InetAddress serverIP = InetAddress.getByName("127.0.0.1");
            int port = 8899;
            //2. 创建一个Socket
            socket = new Socket(serverIP,port);
            //3. 创建一个输出流,向外写东西
            os = socket.getOutputStream();
            os.write("hello,tcp...".getBytes());
        } catch (UnknownHostException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            //4. 关闭资源
            try {
                if (os!=null){
                    os.close();
                }
                if (socket!=null){
                    socket.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

UDP

udp接受端:

package com.xxliao.udp;

import java.net.DatagramPacket;
import java.net.DatagramSocket;

/**
 * @author xxliao
 * @description: UdpReceiver
 * @date 2023/11/19$ 12:54$
 */

public class UdpReceiver {

    public static void main(String[] args) throws Exception{
        //1. 建立DatagramSocket,开放端口
        DatagramSocket socket = new DatagramSocket(9090);
        //2. 接收数据
        byte[] buffer = new byte[1024];
        DatagramPacket packet = new DatagramPacket(buffer,0,buffer.length);
        socket.receive(packet);
        //3. 输出数据
        // packet.getData() : 获取packet中的数据
        System.out.println(new String(packet.getData(), 0,
                packet.getLength()));
        //4. 关闭socket
        socket.close();
    }
}

udp发送端:

package com.xxliao.udp;

import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.net.SocketException;

/**
 * @author xxliao
 * @description: UdpSender
 * @date 2023/11/19$ 12:53$
 */

public class UdpSender {

    public static void main(String[] args) throws Exception {
        //1. 建立DatagramSocket
        DatagramSocket socket = new DatagramSocket();
        //2. 封装数据包
        String msg = "UDPSender==>";
        byte[] data = msg.getBytes();
        InetAddress inet = InetAddress.getByName("127.0.0.1");
        int port = 9090;
        DatagramPacket packet = new
                DatagramPacket(data,0,data.length,inet,port);
        //3. 通过 Socket 发送 packet
        socket.send(packet);
        //4. 关闭socket
        socket.close();
    }
}

URL

举例1:

package com.xxliao.url;

import java.net.MalformedURLException;
import java.net.URL;

/**
 * @author xxliao
 * @description: url demo one 
 * @date 2023/11/19$ 13:01$
 */

public class URLDemo {

    public static void main(String[] args) {
        try {
            URL url = new URL("http://localhost:8080/helloworld/index.jsp? username=kuangshen&password=123");
            System.out.println(url.getProtocol()); //获取URL的协议名
            System.out.println(url.getHost()); //获取URL的主机名
            System.out.println(url.getPort()); //获取URL的端口号
            System.out.println(url.getPath()); //获取URL的文件路径
            System.out.println(url.getFile()); //获取URL的文件名
            System.out.println(url.getQuery()); //获取URL的查询名
        } catch (MalformedURLException e) {
            e.printStackTrace();
        }
    }
}

举例2:

package com.xxliao.url;

import java.io.FileOutputStream;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;

/**
 * @author xxliao
 * @description: url demo two
 * @date 2023/11/19$ 13:02$
 */

public class URLDemo02 {

    public static void main(String[] args) {
        try {
            //1. 定位到服务器端的资源
            URL url = new
                    URL("http://localhost:8080/helloworld/xxliao.jpg");
            //2. 创建连接
            HttpURLConnection connection = (HttpURLConnection)
                    url.openConnection();
            //3. 获取输入流
            InputStream is = connection.getInputStream();
            //4. 写出文件
            FileOutputStream fos = new FileOutputStream("xxliao2.jpg");
            byte[] buffer = new byte[1024];
            int len;
            while ((len=is.read(buffer))!=-1){
                fos.write(buffer,0,len);
            }
            //关闭资源
            fos.close();
            is.close();
            connection.disconnect(); //断开连接
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/669022.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Vue进阶之Vue无代码可视化项目(一)

Vue无代码可视化项目 项目搭建初始步骤拓展:工程项目从0-1项目规范化package.jsoncpell.jsoncustom-words.txtts-eslint规则.eslintrc.cjsgit钩子检查有没有问题type-checkspellchecklint:stylehusky操作安装pre-commitpnpm的commit规范package.json:commitlint.config.cjs安装…

Java数组操作

数组拓展 1.1 数组拷贝 需求:定义一个方法arraycopy, 从指定源数组中从指定的位置开始复制指定数量的元素到目标数组的指定位置。 1.2. 排序操作 需求:完成对int[] arr new int[]{2,9,6,7,4,1}数组元素的升序排序操作. 1.2.1.冒泡排序 对未排序的各元素…

【计算机毕设】基于SpringBoot的教师工作量管理系统设计与实现 - 源码免费(私信领取)

免费领取源码 | 项目完整可运行 | v:chengn7890 诚招源码校园代理! 1. 研究目的 随着高校规模的扩大和教学任务的增加,教师的工作量管理变得越来越复杂和重要。传统的教师工作量管理方式效率低下,容易出错&…

【typescript/flatbuffer】在websocket中使用flatbuffer

目录 说在前面场景fbs服务器代码前端typescript代码问题 说在前面 操作系统:Windows11node版本:v18.19.0typescript flatbuffer版本:24.3.25 场景 服务器(本文为golanggin)与前端通信时使用flatbuffer进行序列化与反序列化通信协议为websock…

CSDN UI 2024.06.01

当我们的栏目很多的时候,通过【置顶】来排列顺序是很麻烦的,应该加一列,设置优先级别。太难用了 或者加两个按钮【上移】 【下移】

正邦科技(day4)

烧录 一、烧录固件二、 通讯模块升级1:USB的方式升级固件2:通过mqtt的方式升级固件3:切换环境 三、 烧录WiFi1:短接2:烧录脚本 设备注意事项: 第一种方式:通信模组和MCU都可以统一烧录BoodLoade…

内网穿透-FRP流量改造

前言 在拿下一台机器作为入口时,内网代理就变得尤为重要。他是我们进行横向渗透一个中间人,没了代理在内网中就寸步难行。而内网穿透的工具有很多,比如frp,reGeorg等等非常优秀的代理工具。使用方法不在赘述,这篇文章…

ssm_mysql_高校自习室预约系统(源码)

博主介绍:✌程序员徐师兄、8年大厂程序员经历。全网粉丝15w、csdn博客专家、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域和毕业项目实战✌ 🍅文末获取源码联系🍅 👇🏻 精彩专栏推荐订阅👇…

Ansible05-Ansible进阶(流程控制、Roles角色、加密优化调优等)

目录 写在前面7 Ansible 进阶7.1 流程控制7.1.1 handlers触发器与notify7.1.1.1 未使用handlers7.1.1.2 使用handlers 7.1.2 when判断7.1.2.1 when的语法7.1.2.2 when判断主机名选择模块输出7.1.2.3 when结合register变量 7.1.3 loop/with_items循环7.1.3.1 with_items案例7.1.…

微信小程序注册流程及APPID,APPSecret获取

1.注册微信小程序 注册链接:公众号 (qq.com) 1.1填写邮箱、密码、验证码 1.2邮箱登录点击邮件中链接激活,即可完成注册 1.3用户信息登记 接下来步骤,将用个人主题类型来进行演示 填写主体登记信息,使用管理员本人微信扫描二维码…

行政工作如何提高效率?桌面备忘录便签软件哪个好

在行政管理工作中,效率的提高无疑是每个行政人员都追求的目标。而随着科技的发展,各种便捷的工具也应运而生,其中桌面备忘录便签软件便是其中的佼佼者。那么,这类软件又如何帮助我们提高工作效率呢? 首先,…

(2024,LoRA,全量微调,低秩,强正则化,缓解遗忘,多样性)LoRA 学习更少,遗忘更少

LoRA Learns Less and Forgets Less 公和众和号:EDPJ(进 Q 交流群:922230617 或加 VX:CV_EDPJ 进 V 交流群) 目录 0. 摘要 1. 引言 2. 背景 3. 实验设置 3.2 使用编码和数学基准测试来衡量学习(目标域…

C++:细谈Sleep和_sleep

ZINCFFO的提醒 还记得上上上上上上上上上上上上上上上上上上(上的个数是真实的)篇文章吗? 随机应变——Sleep()和_sleep() 但在ZINCFFO的C怪谈-02中: 我不喜欢Sleep...... 奤?媜煞鷥! 整活!…

容器项目之前后端分离

容器化部署ruoyi项目 #需要的镜像nginx、java、mysql、redis、 #导入maven镜像、Java镜像和node镜像 docker load -i java-8u111-jdk.tar docker load -i maven-3.8.8-sapmachine-11.tar docker load -i node-18.20.3-alpine3.20.tar #拉取MySQL和nginx镜像 docker pull mysql…

权限修饰符和代码块

一.权限修饰符 1.权限修饰符:是用来控制一个成员能够被访问的范围的。 2.可以修饰成员变量,方法,构造方法,内部类。 3.例子: public class Student {priviate String name;prviate int age;} 二.权限修饰符的分类 有四种作用范围大小…

牛客网刷题 | BC102 带空格直角三角形图案

目前主要分为三个专栏,后续还会添加: 专栏如下: C语言刷题解析 C语言系列文章 我的成长经历 感谢阅读! 初来乍到,如有错误请指出,感谢! 描述 KiKi学习了循环&am…

#1 深度优先搜索

深搜思想 DFS其实是针对图论的一种搜索算法,由一个节点出发,不撞南墙不回头式的遍历所有的节点。 如先遍历1,沿(1,2)遍历2,再沿(2,4)遍历4,撞南墙(边界条件…

bcaktrader策略编写1

。 1 Backtrader策略类编写说明 在上一篇,我大体记录了整个backtrader整体最简流程,策略类中没有实现任何买卖逻辑,只是单纯的打印了每日的收盘价。今天,我将详细介绍策略编写类的构建过程,并构建一个简单的均线策略…

林业调查具体是做些什么?

林业调查是对森林资源进行系统的信息收集和处理的过程。 林业调查涵盖了对林木、林地以及林区内生长的动植物及其环境条件的全面评估,旨在及时掌握森林资源的数量、质量和生长消亡的动态规律。这种调查不仅关注森林本身,还包括与之相关的自然环境和经济…

分销与传销的界限

分销与传销,作为商业活动中的两种销售模式,确实在核心特征和法律地位上存在显著的区别。以下是关于两者的详细分析,以及为什么选择微信分销小程序时,通常建议找外包公司的理由。 一、分销与传销的区别 商业模式: 分销…