JavaEE企业开发新技术5

目录

2.18 综合应用-1

2.19 综合应用-2

2.20 综合应用-3

2.21 综合应用-4

2.22 综合应用-5

Synchronized :


2.18 综合应用-1

反射的高级应用

DAO开发中,实体类对应DAO的实现类中有很多方法的代码具有高度相似性,为了提供代码的复用性,降低冗余度,可以通过反射的方式可以定义一个公共的DAO,只要提供实体类名,就可以得到对应数据库表中的所有记录。

用到的知识点:

(1)JDBC的基本操作

(2)单例设计模式

(3)数据库结果集对应的元数据(ResultSetMeteDate)

(4)反射

命名的规范化要求:

(1)实体类类名每个首字母大写,数据库表字段名称要与实体类属性名称一致,数据库表中字段命名的时候每个单词首字母要大写。

(2)数据库表命名以“t_”开头,后面跟对应的实体类名称,首字母小写。

源码:

package cn.edu.xync.myweb.reflect;

import java.lang.reflect.Method;
import java.security.Timestamp;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.List;

class JDBCUtil{
	private static JDBCUtil util=null;//定义私有的静态成员
	private JDBCUtil() {//加载驱动
		try {
			Class.forName("com.mysql.cj.jdbc.Driver");
		} catch (ClassNotFoundException e) {
			
			e.printStackTrace();
		}
	}
	
	public static JDBCUtil getInstance() {//判断util这个静态成员属性有没有被实例化
		synchronized(JDBCUtil.class) {
			if(util==null) {
				util=new JDBCUtil();//实例化
			}
			return util;
		}	
	}
	
	public Connection getConnection() throws SQLException {//返回链接对象
		return DriverManager.getConnection("jdbc:mysql://localhost:3306/mysqldb?characterEncoding=UTF-8","root","1234567890");
	}
	
	public void close(ResultSet rs, Statement stmt, Connection con) {

		try {
			if (rs != null) // 关闭并释放资源
				rs.close();
			if (stmt != null)
				stmt.close();
			if (con != null)
				con.close();
		} catch (SQLException e) {

			e.printStackTrace();
		}

	}
}

JDBCUtil使用了封装类并使用了单例设计模式

2.19 综合应用-2

class CommonDAO {// 定义公共的DAO
	/*
	 * 根据实体类名将其对应的数据库表中所有的记录封装成实体类集合返回 说明:数据库表字段名称要与实体类属性名称一致,数据库表中字段命名的时候每个单词首字母要大写
	 */
	public List getBeans(String beanName) throws Exception {
		// 得到对应的数据库表名称
		String tableName = this.getTableName(beanName);
		System.out.println(tableName);
		String sql = "select * from " + tableName;// select * from t_account

		List lists = new ArrayList();// 把表里的每一行转换成实体类存放在集合里
		JDBCUtil util = JDBCUtil.getInstance();

		try {
			Connection con = util.getConnection();
			Statement stmt = con.createStatement();
			ResultSet rs = stmt.executeQuery(sql);

			ResultSetMetaData rsmd = rs.getMetaData();// 结果集元数据:通过它能够知道结果集对应的表有几列,
			// 这些列的名称,数据类型等信息都在结果集元数据当中

			// 得到当前表共有几个字段
			int columnCount = rsmd.getColumnCount();

			while (rs.next()) {// 对结果集遍历,每执行一次就要通过反射的方法把对应的实体类的clazz对象创建出来
				// 实体类必须放到cn.xysfxy.sprintboot.entity包中
				Class clazz = Class.forName("cn.edu.xync.myweb.entity." + beanName);// 实例化对象
				Object obj = clazz.newInstance();

//对列进行循环				
for (int i = 1; i <= columnCount; i++) {
					System.out.println(rsmd.getColumnName(i));// 拿到列名
					System.out.println(rsmd.getColumnTypeName(i));// 拿到列对应的数据类型的名称

					// 将数据表字段第一个字母转换成大写,为下边拿到setXXX方法使用
					String methodName = this.firstCharToUppercase(rsmd.getColumnName(i));
					// 根据反射调用setXXX方法给实体类对象属性赋值
					Method method = clazz.getDeclaredMethod("set" + methodName,
							this.getAttributeClassType(rsmd.getColumnTypeName(i)));
//得到setId方法传入的java类型
					// setId




					method.invoke(obj, rs.getObject(i));//传值
				}
				lists.add(obj);// 添加到集合里
			}

		} catch (SQLException e) {
			e.printStackTrace();
		}
		return lists;
	}

	// 根据数据库表中某个列的数据类型返回对应的Java数据类型的Class对象
	private Class getAttributeClassType(String columnType) {
		Class clazz = null;
		if ("VARCHAR".equalsIgnoreCase(columnType))
			clazz = String.class;
		if ("INT".equalsIgnoreCase(columnType))
			clazz = Integer.class;
		if ("Float".equalsIgnoreCase(columnType))
			clazz = Float.class;
		if ("DATETIME".equalsIgnoreCase(columnType))
			clazz = Timestamp.class;
		return clazz;
	}

	// 将数据表列名第一个字母转换成大写
	private String firstCharToUppercase(String columnName) {
		String uppercaseString = columnName.toUpperCase();
		char firstChar = uppercaseString.charAt(0);
		String firstCharString = String.valueOf(firstChar);
		return firstCharString.concat(columnName.substring(1, columnName.length()));
	}

	/*
	 * 根据实体类名称得到对应的数据表名称 命名必须遵守的规范 例如Account,对应的表名称为t_account
	 */

	private String getTableName(String beanName) {
		char oldFirstChar = beanName.charAt(0);
		// 实体类名首字母先转换成字符串形式,再转换成小写
		String newFirstChar = String.valueOf(oldFirstChar).toLowerCase();
		// 拼接字符串
		String tableName = "t_" + beanName.replaceFirst(String.valueOf(oldFirstChar), newFirstChar);//替换字符
		return tableName;// 把Account-->t_account
	}
}

2.20 综合应用-3

2.21 综合应用-4

public class GenericTest {
	public static void main(String[] args) {
		CommonDAO dao = new CommonDAO();
		List lists = null;
		try {
			lists = dao.getBeans("User");
			// lists=dao.getBeans("Goods");
			
			for(int i=0;i<lists.size();i++) {
				System.out.println(lists.get(i));
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}

运行结果:

总结:这是通过反射和JDBC结果集元数据相结合的一个例子,目的:减少代码的冗余,提高代码的复用性

2.22 综合应用-5

一般我们不会去传递类的名称,我们都是传递类的Class对象

applicationContext.getBean(XXX.class)

private String getTableName(Class beanType) {
		//String beanNameWithPackage=beanType.getName();//得到的类名包含了package信息
		String beanName=beanType.getSimpleName();//得到Account
		System.out.println(beanName);
//		//cn.xxx.xxx.Account
//		System.out.println(beanNameWithPackage);
//		String subName[] =beanNameWithPackage.split("\\.");//按.转义拆分成字符串数组
//		String beanName=subName[subName.length-1];//拿到最后一个字符串
		
		char oldFirstChar = beanName(0);
		// 实体类名首字母先转换成字符串形式.charAt,再转换成小写
		String newFirstChar = String.valueOf(oldFirstChar).toLowerCase();
		// 拼接字符串
		String tableName = "t_" + beanName.replaceFirst(String.valueOf(oldFirstChar), newFirstChar);
		return tableName;// 把Account-->t_account
	}

//因为我们传递进来的就是Class对象,所以直接调用newInstance()方法就行

运行结果:

Synchronized :

当多个并发线程(thread1和thread2)访问同一个对象(ThreadSyn)中的synchronized代码块时,就相当于对这个代码块加了锁,在同一时刻只能有一个线程得到执行,其他线程受阻塞,必须等待当前线程执行完这个代码块以后才能执行该代码块。

当多个线程访问 不同对象 的同步代码块,线程访问各自同步代码块,线程不会阻塞,互不干扰。

总结

1、无论synchronized关键字加在方法上还是对象上,如果它作用的对象是非静态的,则它取得的锁是对象;如果synchronized作用的对象是一个静态方法或一个类,则它取得的锁是对类,该类所有的对象同一把锁。

2、每个对象只有一个锁(lock)与之相关联,谁拿到这个锁谁就可以运行它所控制的那段代码。

3、实现同步是要很大的系统开销作为代价的,甚至可能造成死锁,所以尽量避免无谓的同步控制。

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

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

相关文章

【STL】迭代器iterator详解

前言 本篇文章以对string的操作来演示迭代器的操作。 一、什么是迭代器iterator&#xff1f; 迭代器&#xff08;iterator&#xff09;是一种可以遍历容器元素的数据类型。迭代器是一个变量&#xff0c;相当于容器和操纵容器的算法之间的中介。C迭代器是一种用于遍历容器中元的…

【Modelsim】保持波形格式重编译and波形的保存与查看

文章目录 保持原波形格式重编译波形的保持与查看保存波形打开工程查看波形 保持原波形格式重编译 Modelsim 仿真设置好波形格式后&#xff0c;若需要修改代码并保持原波形格式重新查看波形&#xff0c;只需将文件重新编译后仿真即可。 1.修改代码后Project页面的代码状态变成…

lua学习笔记20(lua中一些自带库的学习)

print("*****************************lua中一些自带库的学习*******************************") print("*************时间***************") --系统时间 print(os.time()) --自己传入参数得到时间 print(os.time({year2011,month4,day5})) --os.data(&qu…

包装类初识泛型

一.包装类 在Java中, 基本类型不继承于Object类. 所以为了在泛型代码中可以支持基本类型,Java给每个基本类型都对应了一个包装类型.(包装类型相当于引用类型) 1.基本类型对应的包装类 byte -- Byteshort -- Shortint -- Integerlong -- Longfloat -- Floatdouble -- Doublech…

Vue2 基础学习-案例实践

数据管理信息的增删改查的实践 主要应用&#xff1a; 数据插值&#xff1a; {{xxx}}双向绑定&#xff1a;v-model点击事件函数&#xff1a;click列表xxx的增删改实现 xxx.push(row) 增加xxx.splice(id,1) 删除 一行{x,y} xxx[id]; 编辑 <!DOCTYPE html> <html la…

蓝桥杯 2019 省A 糖果 动态规划/二进制

#include <bits/stdc.h> // 包含标准库中的所有头文件 using namespace std;int main() {int n,m,k; // 定义变量n&#xff08;糖果包数&#xff09;、m&#xff08;口味数&#xff09;、k&#xff08;每包糖果的个数&#xff09;cin>>n>>m>>k; // 输入…

[lesson31]完善的复数类

完善的复数类 完善的复数类 复数类应该具有的操作 运算&#xff1a;&#xff0c;-&#xff0c;*&#xff0c;/比较&#xff1a;&#xff0c;!赋值&#xff1a;求模&#xff1a;modulus 利用操作符重载 统一复数与实数的运算方式统一复数与实数的比较方式 注意事项 C规定赋…

Day 25 组合(优化)216.组合总和III 17.电话号码的字母组合

组合&#xff08;优化&#xff09; 先给出组合问题的回溯部分代码&#xff1a; vector<vector<int>> result; // 存放符合条件结果的集合vector<int> path; // 用来存放符合条件结果void backtracking(int n, int k, int startIndex) {if (path.size() k) …

洛谷P1305 新二叉树

Java 代码 import java.util.Scanner;public class Main {public static void main(String[] args) {Scanner sc new Scanner(System.in);int n sc.nextInt();char arr[][] new char[n][3];for (int i 0; i < n; i) {String strsc.next();char arr1[]str.toCharArray()…

【计算机考研】跨考计算机,需要准备多久才来得及?

9个月跨考计算机&#xff0c;如果选择是408的话&#xff0c;时间稍微有点紧张&#xff0c;前期感觉不大&#xff0c;后期数学408堆在一起会感觉很难受... 很多确定考408的同学都是一开始先从数据结构开始复习的&#xff0c;这样到了中后期觉得自己时间不够了再去转自命题也来得…

UE5数字孪生系列笔记(四)

场景的切换 创建一个按钮的用户界面UMG 创建一个Actor&#xff0c;然后将此按钮UMG添加到组件Actor中 调节几个全屏的背景 运行结果 目标点切换功能制作 设置角色到这个按钮的位置效果 按钮被点击就进行跳转 多个地点的切换与旋转 将之前的目标点切换逻辑替换成旋转的逻…

使用webpack5+TypeScript+npm发布组件库

一、前言 作为一只前端攻城狮&#xff0c;没有一个属于自己的组件库&#xff0c;那岂不是狮子没有了牙齿&#xff0c;士兵没有了武器&#xff0c;姑娘没有了大宝SOD蜜&#xff0c;你没有了我.... 言归正传&#xff0c;下面将给大家介绍如何通过webpack5编译一个TS组件发布到NPM…

Cannot find runner for app ——Android Studio

问题 在修改build.gradle(:app)文件或者其他操作后&#xff0c;出现了无法运行的问题&#xff1a; Cannot find runner for app 如图运行按钮不可点击。 解决方案 点击【File】下的【Sync Project with Gradle Files】同步完成后&#xff0c;一般就可运行了。

树形侧边栏(展开、全选、切换名称)

父文件&#xff1a; index.vue <template><div class"h-full p20px bg-#f5f5f5"><ContentWrap class"w-260px h-[calc(100vh-200px)] min-h-700px"><TenantTree select"tentantSelect" /></ContentWrap></div&…

ExtendSim花生酱加工厂模型

该模型展示了ExtendSim可靠性模块与ExtendeSim离散速率技术相结合的协同作用。 在花生酱加工厂的最初阶段&#xff0c;花生经过烘烤和冷却。冷却后的花生经过热烫或水烫去外皮。这些经过漂白的花生进入过程的混合部分&#xff0c;在研磨机中用盐、葡萄糖和氢化油稳定剂将其粉碎…

链表基础3——单链表的逆置

链表的定义 #include <stdio.h> #include <stdlib.h> typedef struct Node { int data; struct Node* next; } Node; Node* createNode(int data) { Node* newNode (Node*)malloc(sizeof(Node)); if (!newNode) { return NULL; } newNode->data …

【七 (1)指标体系建设-构建高效的故障管理指标体系】

目录 文章导航一、故障概述1、故障&#xff1a;2、故障管理&#xff1a; 二、指标体系概述1、指标2、指标体系 三、指标体系构建难点1、管理视角2、业务视角3、技术视角 四、指标体系构建原则1、与战略目标对齐2、综合和平衡3、数据可获得性4、可操作性5、具体和可衡量6、参与和…

Windows10为Git Bash添加文件传输命令rsync(详细图文配置)

文章目录 1. 安装git bash2. 下载所需要的4个包3. 下载解压包的软件4. 复制每个包下面的usr到git安装目录下4.1 所遇问题4.2 解决 5. 安装完成6. 需要注意 Windows上要使用 rsync命令上传或下载文件&#xff0c;需要使用git bash&#xff0c;git bash没有rsync&#xff0c;需要…

盘点2024年最新可用免费云服务器

随着云计算技术的快速发展&#xff0c;越来越多的企业和个人开始使用云服务器来满足各种业务需求。云服务器作为云计算的核心服务之一&#xff0c;以其弹性扩展、按需付费等特点受到广泛关注。本文将为大家盘点2024年最新可用免费云服务器&#xff0c;助力大家轻松上云&#xf…

Problem #8 [Easy]

This problem was asked by Google. A unival tree (which stands for “universal value”) is a tree where all nodes under it have the same value. Given the root to a binary tree, count the number of unival subtrees. For example, the following tree has 5 un…