Java基础系列:Class.forName、static及应用

1 简介

源码:
在这里插入图片描述

(1)Class.forName(String name)生成指定类名或接口名的类对象(Class)。与方法等价:Class.forName(className, true, currentLoader),
currentLoader即定义当前类的类加载器。
(2)Class.forName:在方法区生成java.lang.Class对象。即类加载过程:通过全限定名获取类的二进制字节流,将二进制字节流转化为方法区的运行时数据结构。
(3)生成Class对象后,即可执行不依赖对象的静态块代码,如MySQL驱动的加载。

2 static

调用时不依赖实例化的对象。
变量或方法使用static关键字,调用时,无需new对象,使用类名即可。
类加载时,根据生成的Class对象完成调用。

3 Usage

3.1 静态代码块

package com.monkey.java_study.common.entity;

/**
 * User实体
 *
 * @author xindaqi
 * @since 2021-01-23
 */

public class UserEntity {

    /**
     * 用户id
     */
    private String uid;

    /**
     * 用户名称
     */
    private String nickname;

    /**
     * 用户性别
     */
    private String sex = "haha";

    public UserEntity() {
    }

    static {
        System.out.println(">>>>>>>>static function");
    }
    // 省略setter/getter/toString()
}

3.2 Class.forName()生成Class对象

使用Class.forName(String name)生成Class时,类加载过程中会直接调用静态代码块。

package com.monkey.java_study.database;

import com.monkey.java_study.common.entity.UserEntity;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

/**
 * Class.forName测试.
 *
 * @author xindaqi
 * @date 2021-12-30 17:35
 */
public class DriverLoaderTest {

    private static final Logger logger = LogManager.getLogger(DriverLoaderTest.class);

    public static void main(String[] args) throws Exception {
        Class userClass = Class.forName("com.monkey.java_study.common.entity.UserEntity");
    }
}

执行结果:
在这里插入图片描述

3.3 MySQL驱动加载

MySQL注册驱动时,通过Class.forName(“com.mysql.cj.jdbc.Driver”)即完成了驱动注册。
代码如下:

package com.monkey.java_study.database;

import com.monkey.java_study.common.entity.UserEntity;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;

import static com.monkey.java_study.common.constant.DatabaseConstant.*;
import static com.monkey.java_study.common.constant.DatabaseConstant.DB_MYSQL_PASSWORD;

/**
 * Class.forName测试.
 *
 * @author xindaqi
 * @date 2021-12-30 17:35
 */
public class DriverLoaderTest {

    private static final Logger logger = LogManager.getLogger(DriverLoaderTest.class);

    public static Connection databaseConnection() throws Exception {
        // 注册MySQL驱动
        Class.forName("com.mysql.cj.jdbc.Driver");
        // 数据库连接地址
        String DB_MYSQL_URL = "jdbc:mysql://localhost:3306/db_monkey_run?useUnicode=true&characterEncoding=UTF-8&useSSL=false&serverTimezone=Asia/Shanghai";
        // 数据库用户名
        String DB_MYSQL_USER_NAME = "root";
        //数据库密码
        String DB_MYSQL_PASSWORD = "123456";
        return DriverManager.getConnection(DB_MYSQL_URL, DB_MYSQL_USER_NAME, DB_MYSQL_PASSWORD);
    }

    public static void main(String[] args) throws Exception {
        Class userClass = Class.forName("com.monkey.java_study.common.entity.UserEntity");
        Connection connection = databaseConnection();
    }
}

这是为什么?
因为Driver驱动类中有一段静态代码块。静态代码块中通过DriverManager完成驱动注册,即:java.sql.DriverManager.registerDriver(new Driver());
源码如下:

/*
 * Copyright (c) 2002, 2018, Oracle and/or its affiliates. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify it under
 * the terms of the GNU General Public License, version 2.0, as published by the
 * Free Software Foundation.
 *
 * This program is also distributed with certain software (including but not
 * limited to OpenSSL) that is licensed under separate terms, as designated in a
 * particular file or component or in included license documentation. The
 * authors of MySQL hereby grant you an additional permission to link the
 * program and your derivative works with the separately licensed software that
 * they have included with MySQL.
 *
 * Without limiting anything contained in the foregoing, this file, which is
 * part of MySQL Connector/J, is also subject to the Universal FOSS Exception,
 * version 1.0, a copy of which can be found at
 * http://oss.oracle.com/licenses/universal-foss-exception.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 * FOR A PARTICULAR PURPOSE. See the GNU General Public License, version 2.0,
 * for more details.
 *
 * You should have received a copy of the GNU General Public License along with
 * this program; if not, write to the Free Software Foundation, Inc.,
 * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301  USA
 */

package com.mysql.cj.jdbc;

import java.sql.SQLException;

/**
*  省略了注释
 */
public class Driver extends NonRegisteringDriver implements java.sql.Driver {
    //
    // Register ourselves with the DriverManager
    //
    static {
        try {
            java.sql.DriverManager.registerDriver(new Driver());
        } catch (SQLException E) {
            throw new RuntimeException("Can't register driver!");
        }
    }

    /**
     * Construct a new driver and register it with DriverManager
     * 
     * @throws SQLException
     *             if a database error occurs.
     */
    public Driver() throws SQLException {
        // Required for Class.forName().newInstance()
    }
}

4 小结

  • 方法区:静态区。装载class文件,存储类信息、常量和静态变量;静态代码块同样存储与方法区,不依赖于实例化的对象;
  • Class.forName即在方法区加载指定的类,生成Class对象,同时直接加载类的静态代码块。

【参考文献】
[1]https://blog.csdn.net/qq_22059611/article/details/84347957
[2]https://www.cnblogs.com/dolphin0520/p/3799052.html

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

天然玩家

坚持才能做到极致

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值