[Spring+SpringMVC+Mybatis]框架学习笔记(九):Mybatis主配置文件和映射文件
第9章 Mybatis主配置文件和映射文件
9.1 用Mybatis进行开发的两种方式
在正式的开发环境中用Mybatis进行开发有两种方式:
1)原始的接口和实现类的方式
缺点:
- 重复代码太多,sqlSession的操作
- statement的id硬编码将来影响维护
2)基于mapper代理的开发方式(重点)
mybatis根据一些规则自动创建dao接口的实现类的代理对象
规则:
- userMapper.xml中namespace必须指定为UserMapper(相当于第8讲案例中的IUserDao)的全限定类名
- userMapper.xml中statement(即sql语句)的id指定为UserMapper接口中对应的方法名称
- userMapper.xml中statement的输入参数类型和UserMapper中对应的方法参数类型一致
- userMapper.xml中statement的返回类型和UserMapper中的对应方法的返回类型一致
9.2 主配置文件config.xml详解
* properties标签
主要用于配置数据库的连接数据
* settings 全局的配置参数
mybatis中的运行时行为设置 ,比如缓存的开启,驼峰命名的映射,延迟加载的设置等等
* plugins
mybatis需要引入的一些插件 :分页插件pageHelper
* enviroments
环境配置,可以配置多种数据库连接
* mapper
详见mybatis-config.xml
9.3 映射文件mapper.xml详解
输入参数parameterType
- 简单类型的单个参数
需求:根据用户id查询用户信息 - 简单类型的多个参数
需求:通过登录名和密码验证用户是否存在 - 包装类对象作为输入参数进行查询
需求:根据界面输入的用户名称或者登录名称来查询符合条件的用户列表
- 简单类型的单个参数
动态sql
- if标签和where标签
- sql片段
- foreach
输出参数resultType/resultMap
- 简单类型的输出 Integer(可写为int,即用别名,该别名是自动设置的,不需要在主配置文件中设置) String Long(可写为long)
- 对象的输出
- HashMap的输出
- resultMap对象输出(当数据库设计时没有遵循命名规则,java设计也没有遵循命名规则时使用 --> 手动设置数据库表列名与java属性之间的对应关系)
9.4 基于mapper代理的Mybatis的Demo
9.4.1 测试数据准备
jdbc的属性配置文件:
jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://127.0.0.1:3306/mybatis_test
jdbc.user=root
jdbc.password=123
9.4.2 User实体类、Dao接口
User实体类与8.4.2相同。
包装类UserDto:
package com.steven.mybatis.sysmanage.dto;
import com.steven.mybatis.sysmanage.entity.User;
/**
* 跟数据库M_USER表对应的实体类
* @author chenyang
*
*/
public class UserDto implements java.io.Serializable{
private static final long serialVersionUID = 1L;
private User user;
public User getUser(){
return user;
}
public void setUser(User user){
this.user = user;
}
}
Dao接口UserMapper基本与8.4.2相同,这里增加了几个方法。
package com.steven.mybatis.sysmanage.mapper;
import java.util.List;
import java.util.Map;
import com.steven.mybatis.sysmanage.dto.UserDto;
import com.steven.mybatis.sysmanage.entity.User;
/**
* 定义用户增删改查dao接口
* @author chenyang
*
*/
public interface UserMapper {
/**
* 根据用户id获取用户对象信息
* @param userId
* @return
*/
public User getUserById(Long userId);
/**
* 通过登录名和密码来验证用户是否存在
* @param loginName
* @param password
* @return
*/
public User getUserByLoginNameAndPsd(String loginName, String password);
/**
* 通过用户实体包装类来进行查询
* @param userDto
* @return
*/
public List<User> getUserListByUserDto(UserDto userDto);
/**
* 获取所有用户数目
* @return
*/
public Integer getUserCount();
/**
* 查询所有用户数据,以map结构数据返回
* @return
*/
public List<Map<Object, Object>> getUserListMap();
/**
* 查询所有用户数据,用resultMap返回结果集
* @return
*/
public List<User> getUserListByResultMap();
/**
* 查询所有用户数据,查询所有用户对象
* @return
*/
public List<User> getUserList();
/**
* 增加用户对象
* @param user
*/
public void addUser(User user);
/**
* 删除用户对象
* @param user
*/
public void delUser(User user);
/**
* 修改用户对象
* @param user
*/
public void updateUser(User user);
}
9.4.3 Mybatis的主配置文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<properties resource="jdbc.properties"></properties>
<settings>
<!-- 是否开启自动检测驼峰命名规则,如USER_ID userId
即从经典的数据表列名AB_COLUMN到经典的java属性名的映射abColumn
默认是false
-->
<setting name="mapUnderscoreToCamelCase" value="true"></setting>
</settings>
<!-- 设置别名 -->
<typeAliases>
<!-- 单个设置别名 -->
<!-- <typeAlias type="com.steven.mybatis.sysmanage.entity.User" alias="user"/> -->
<!-- 批量设置别名 -->
<package name="com.steven.mybatis.sysmanage.entity"/>
</typeAliases>
<!-- 默认引用那个数据库环境 -->
<environments default="defaultEnv">
<environment id="defaultEnv">
<!-- 事务管理方式 -->
<transactionManager type="JDBC"></transactionManager>
<!-- 数据库连接四要素 -->
<dataSource type="POOLED">
<property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.user}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>
</environment>
</environments>
<!-- 加入所有的sql映射文件 -->
<mappers>
<!-- 第一种方式,用resource属性,注意目录用/分隔 -->
<!-- <mapper resource="com/steven/mybatis/sysmanage/mapper/UserMapper.xml"></mapper> -->
<!-- 第二种方式,用class属性应用接口类,规则:接口类和sql映射文件必须同名,然后在同一路径 -->
<!-- <mapper class="com.steven.mybatis.sysmanage.mapper.UserMapper"></mapper> -->
<!-- 第三种方式,用package标签批量自动扫描所配置的包路径的所有接口
规则:接口类和sql映射文件必须同名,然后在同一路径-->
<package name="com.steven.mybatis.sysmanage.mapper"></package>
</mappers>
</configuration>
9.4.4 对象映射文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.steven.mybatis.sysmanage.mapper.UserMapper">
<select id="getUserById" parameterType="long" resultType="user">
SELECT USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE FROM M_USER
WHERE USER_ID=#{ID}
</select>
<!-- 通过登录名和密码验证用户是否存在 -->
<select id="getUserByLoginNameAndPsd" resultType="user">
SELECT USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE FROM M_USER
WHERE LOGIN_NAME=#{0} AND PASSWORD=#{1}
</select>
<!-- 通过包装类UserDto的条件来查询用户列表-->
<!-- 当我们根据过滤条件查询时,如果需要用到模糊查询,我们不能用占位符#{},
得用${}拼接将查询的sql和参数拼接起来
注意:拼接符容易引起sql注入和sql执行效率问题,慎用!
能用占位符就不用拼接符
-->
<select id="getUserListByUserDto" parameterType="com.steven.mybatis.sysmanage.dto.UserDto" resultType="user">
SELECT USER_ID,USER_NAME,LOGIN_NAME,PASSWORD,DEPT_ID,BIRTHDAY,TV_UPDATE FROM M_USER
<!-- where标签有两个用途:1:添加sql的where关键字;2:判断第一个条件不需要and -->
<where>
<if test="user!=null">
<if test="user.loginName!=null">AND LOGIN_NAME LIKE '%${user.loginName}%'</if>
<if test="user.userName!=null">AND USER_NAME LIKE '%${user.userName}%'</if>
<if test="user.birthday!=null">AND BIRTHDAY=#{user.birthday}</if>
<if test="user.deptId!=null">AND DEPT_ID=#{user.deptId}</if>
</if>
</where>
</select>
<!-- 查询用户数目 -->
<select id="getUserCount" resultType="int">
SELECT COUNT(0) FROM M_USER
</select>
<!-- 查询所有用户信息 -->
<select id="getUserList" resultType="user">
SELECT USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE FROM M_USER
</select>
<!-- 查询所有用户信息,用map返回-resultType -->
<select id="getUserListMap" resultType="hashMap">
SELECT USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE FROM M_USER
</select>
<!-- 定义一个resultMap id="userResultMap" -->
<resultMap type="user" id="userResultMap">
<!-- id标签代表数据库的主键;column代表列名或者sql中的别名;property代表java对象的属性名 -->
<!-- 当数据库字段名和java类属性名遵循了命名规则时,下面的对应关系可以省略不用写 -->
<id column="ID" property="userId"></id>
<result column="USER_NAME" property="userName"></result>
<result column="LOGIN_NAME" property="loginName"></result>
<result column="BIRTHDAY" property="birthday"></result>
<result column="TV_UPDATE" property="tvUpdate"></result>
</resultMap>
<!-- 查询所有用户信息,以resultMap方式返回 -->
<select id="getUserListByResultMap" resultMap="userResultMap">
SELECT USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE FROM M_USER
</select>
<!-- 增加用户记录 -->
<insert id="addUser" parameterType="user">
INSERT INTO M_USER(USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE)
VALUES(#{userName},#{loginName},#{birthday},#{tvUpdate})
</insert>
<!-- 删除用户 -->
<delete id="delUser" parameterType="user">
DELETE FROM M_USER WHERE USER_ID=#{userId}
</delete>
<!-- 修改用户 -->
<update id="updateUser" parameterType="user">
UPDATE M_USER SET USER_NAME=#{userName},LOGIN_NAME=#{loginName},
BIRTHDAY=#{birthday} WHERE USER_ID=#{userId}
</update>
</mapper>
9.4.5 测试
package com.steven.mybatis.sysmanage.test;
import java.io.IOException;
import java.io.InputStream;
import java.util.List;
import java.util.Map;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.apache.log4j.Logger;
import org.junit.Before;
import org.junit.Test;
import com.steven.mybatis.sysmanage.dto.UserDto;
import com.steven.mybatis.sysmanage.entity.User;
import com.steven.mybatis.sysmanage.mapper.UserMapper;
public class MyBatisMapperTest {
static Logger log = Logger.getLogger(MyBatisMapperTest.class);
private SqlSessionFactory sqlSessionFactory;
private SqlSession sqlSession;
@Before
public void init() throws IOException{
String configFile = "mybatis-config.xml";
InputStream inputStream = Resources.getResourceAsStream(configFile);
sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
sqlSession = sqlSessionFactory.openSession();
}
//根据用户id查询用户,明细信息
@Test
public void testGetUserById(){
//在用mapper代理方式进行开发的时候,通过sqlSession.getMapper获取接口的实现类
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
log.info(userMapper.getUserById(1L));
}
//根据用户名和密码验证用户是否存在
@Test
public void testGetUserByLoginNameAndPsw(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
log.info(userMapper.getUserByLoginNameAndPsd("lilei", "abc"));
}
//根据UserDto对象验证用户是否存在
@Test
public void testGetUserListByUserDto(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
UserDto userDto = new UserDto();
// User user = new User();
// user.setLoginName("Steven");
// userDto.setUser(user); 如果不设置属性,就返回全部
log.info(userMapper.getUserListByUserDto(userDto));
}
//查询用户总数
@Test
public void testGetUserCount(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
log.info(userMapper.getUserCount());
}
//查询所有用户:
//方式一:测试返回结果为User的对象格式
@Test
public void testGetUserList(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
List<User> userList = userMapper.getUserList();
log.info(userList);
}
//方式二:测试返回结果为hashmap的对象格式
@Test
public void testGetUserListMap(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
List<Map<Object,Object>> userListMap = userMapper.getUserListMap();
log.info(userListMap);
}
//方式三:测试resultMap的返回结果
@Test
public void testGetUserListByResultMap(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
List<User> userList = userMapper.getUserListByResultMap();
log.info(userList);
}
//增、删、改省略
}
查询所有用户三种方式结果对比:
方式一:getUserList
[User [userId=1, userName=chenyang, loginName=Steven, password=null, deptId=null, birthday=1986-09-18 00:00:00.0, tvUpdate=2018-02-28 00:00:00.0], User [userId=2, userName=lilei, loginName=lilei, password=null, deptId=null, birthday=1989-09-10 00:00:00.0, tvUpdate=2018-02-28 00:00:00.0], User [userId=4, userName=zhangsan, loginName=Jerry, password=null, deptId=null, birthday=1990-10-03 00:00:00.0, tvUpdate=2018-02-28 00:00:00.0]]
方式二:getUserListMap(它是根据sql语句中要select的字段来显示,sql中没有PASSWORD和DEPT_ID,所有结果中也没有这两个结果)
[{USER_ID=1, TV_UPDATE=2018-02-28 00:00:00.0, USER_NAME=chenyang, LOGIN_NAME=Steven, BIRTHDAY=1986-09-18 00:00:00.0}, {USER_ID=2, TV_UPDATE=2018-02-28 00:00:00.0, USER_NAME=lilei, LOGIN_NAME=lilei, BIRTHDAY=1989-09-10 00:00:00.0}, {USER_ID=4, TV_UPDATE=2018-02-28 00:00:00.0, USER_NAME=zhangsan, LOGIN_NAME=Jerry, BIRTHDAY=1990-10-03 00:00:00.0}]
方式三:getUserListByResultMap(第一种方式与第三种方式返回结果一致)
[User [userId=1, userName=chenyang, loginName=Steven, password=null, deptId=null, birthday=1986-09-18 00:00:00.0, tvUpdate=2018-02-28 00:00:00.0], User [userId=2, userName=lilei, loginName=lilei, password=null, deptId=null, birthday=1989-09-10 00:00:00.0, tvUpdate=2018-02-28 00:00:00.0], User [userId=4, userName=zhangsan, loginName=Jerry, password=null, deptId=null, birthday=1990-10-03 00:00:00.0, tvUpdate=2018-02-28 00:00:00.0]]
9.5 动态sql
- if标签和where标签
例见9.4. - foreach
需求:需要查询指定id集合的所有用户信息
SELECT * FROM M_USER WHERE USER_ID IN (1,2,3)
- sql片段
将通用的sql语句提取出来,称为sql片段,给不同方法应用 - 增加记录返回主键
<!--以oracle数据库为例,需要调用序列 -->
<!-- <selectKey keyProperty="userId" resultType="long" order="BEFORE">
SELECT IDSEQUENCE.NEXTVAL FROM DUAL
</selectKey>
INSERT INTO M_USER(USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE)
VALUES(#{userId},#{userName},#{loginName},#{birthday},#{tvUpdate}) -->
<!-- 以mysql为例 -->
<selectKey keyProperty="userId" resultType="long" order="AFTER">
SELECT LAST_INSERT_ID() AS userId
</selectKey>
INSERT INTO M_USER(USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE)
VALUES(#{userName},#{loginName},#{birthday},#{tvUpdate})
- 在UserDto包装类中增加ids属性
package com.steven.mybatis.sysmanage.dto;
import java.util.List;
import com.steven.mybatis.sysmanage.entity.User;
/**
* 跟数据库M_USER表对应的实体类
* @author chenyang
*
*/
public class UserDto implements java.io.Serializable{
private static final long serialVersionUID = 1L;
private User user;
private List<Long> ids;
public User getUser(){
return user;
}
public void setUser(User user){
this.user = user;
}
public List<Long> getIds() {
return ids;
}
public void setIds(List<Long> ids) {
this.ids = ids;
}
}
- mapper文件
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
<mapper namespace="com.steven.mybatis.sysmanage.mapper.UserMapper">
<select id="getUserListByUserDto" parameterType="com.steven.mybatis.sysmanage.dto.UserDto" resultType="user">
SELECT
<include refid="user_column"></include>
FROM M_USER
<!-- where标签有两个用途:1:添加sql的where关键字;2:判断第一个条件不需要and -->
<where>
<include refid="query_user_sql_where"></include>
</where>
</select>
<!--将通用的sql语句提取出来,称为sql片段,给不同方法复用 -->
<sql id="query_user_sql_where">
<if test="user!=null">
<if test="user.loginName!=null">AND LOGIN_NAME LIKE '%${user.loginName}%'</if>
<if test="user.userName!=null">AND USER_NAME LIKE '%${user.userName}%'</if>
<if test="user.birthday!=null">AND BIRTHDAY=#{user.birthday}</if>
<if test="user.deptId!=null">AND DEPT_ID=#{user.deptId}</if>
</if>
<!-- 需求:实现sql的where部分: AND USER_ID IN(1,2,3) -->
<if test="ids!=null">
<!-- collection:输入参数的属性;open:循环前的开始符合;close:循环后的结束符合 -->
<foreach collection="ids" open="AND USER_ID IN(" close=")" item="id" separator=",">
#{id}
</foreach>
</if>
</sql>
<!-- slq语句中的列名也可以复用 -->
<sql id="user_column">USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE</sql>
<sql id="user_column_with_alisas">A.USER_ID,A.USER_NAME,A.LOGIN_NAME,A.BIRTHDAY,A.TV_UPDATE</sql>
<insert id="addUser" parameterType="user">
<!-- 以mysql为例,由于mysql中可以用到自增长,USER_ID是自增长,需求:返回userId值 -->
<selectKey keyProperty="userId" resultType="long" order="AFTER">
SELECT LAST_INSERT_ID() AS userId
</selectKey>
INSERT INTO M_USER(USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE)
VALUES(#{userName},#{loginName},#{birthday},#{tvUpdate})
<!--以oracle数据库为例,没有自增长,需要调用序列 -->
<!-- <selectKey keyProperty="userId" resultType="long" order="BEFORE">
SELECT IDSEQUENCE.NEXTVAL FROM DUAL
</selectKey>
INSERT INTO M_USER(USER_ID,USER_NAME,LOGIN_NAME,BIRTHDAY,TV_UPDATE)
VALUES(#{userId},#{userName},#{loginName},#{birthday},#{tvUpdate}) -->
</insert>
</mapper>
- 测试
package com.steven.mybatis.sysmanage.test;
import java.io.IOException;
import java.io.InputStream;
import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.List;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.apache.log4j.Logger;
import org.junit.Before;
import org.junit.Test;
import com.steven.mybatis.sysmanage.dto.UserDto;
import com.steven.mybatis.sysmanage.entity.User;
import com.steven.mybatis.sysmanage.mapper.UserMapper;
public class MyBatisMapperTest {
static Logger log = Logger.getLogger(MyBatisMapperTest.class);
private SqlSessionFactory sqlSessionFactory;
private SqlSession sqlSession;
@Before
public void init() throws IOException{
String configFile = "mybatis-config.xml";
InputStream inputStream = Resources.getResourceAsStream(configFile);
sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
sqlSession = sqlSessionFactory.openSession();
}
//根据UserDto对象验证用户是否存在
@Test
public void testGetUserListByUserDto(){
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
UserDto userDto = new UserDto();
// User user = new User();
// user.setLoginName("Steven");
// userDto.setUser(user);
List<Long> ids = new ArrayList<Long>();
ids.add(1L);
ids.add(2L);
ids.add(3L);
userDto.setIds(ids);
log.info(userMapper.getUserListByUserDto(userDto));
}
@Test
public void testAddUser() throws IOException{
User user = new User();
user.setUserName("wangwu");
user.setLoginName("ww");
user.setBirthday(new Timestamp(System.currentTimeMillis()));
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
userMapper.addUser(user);
//测试通过mapper配置文件中的selectKey标签返回userId
log.info(user.getUserId());
//注意:增删改操作的时候,需要提交事务 sqlSession.commit();
sqlSession.commit();
sqlSession.close();
}
}
[Spring+SpringMVC+Mybatis]框架学习笔记(九):Mybatis主配置文件和映射文件的更多相关文章
- 03 Mybatis框架---学习笔记1--框架的概念及优势
1.框架的概念 框架其实就是某种应用的半成品,就是一组组件,供你选用完成你自己的系统.简单说就是使用别人搭好的舞台,你来做表演.而且,框架一般是成熟的,不断升级的软件.框架是我们软件开发中的一套解决方 ...
- Mybatis学习笔记(九) —— Mybatis逆向工程
一.什么是Mybatis逆向工程? 简单的解释就是通过数据库中的单表,自动生成java代码. 我们平时在使用Mabatis框架进行Web应用开发的过程中,需要根据数据库表编写对应的Pojo类和Mapp ...
- 框架学习笔记之Mybatis(一)
一.简介 MyBatis 是一款优秀的持久层框架,它支持定制化 SQL.存储过程以及高级映射.MyBatis 避免了几乎所有的 JDBC 代码和手动设置参数以及获取结果集.MyBatis 可以使用简单 ...
- [Spring+SpringMVC+Mybatis]框架学习笔记(六):事务
第7讲 事务 7.1 事务的概念 事务是一系列作为一个逻辑单元来执行的操作集合. 它是数据库维护数据一致性的单位,它讲数据库从一个一致状态,转变为新的另外一个一致状态.说的简单一点就是:如果一组处理步 ...
- 框架学习笔记之Mybatis(二)
一.动态sql 通过mybatis提供的标签,实现sql语句的拼接. 1.where <select id="findUserList" parameterType=&quo ...
- Mybatis框架学习总结-优化Mybatis配置文件中的配置
连接数据库的配置单独放在一个properties文件中 之前,是直接将数据库的连接配置信息卸载了Mybatis的conf.xml文件中,如下: <?xml version="1.0&q ...
- Mybatis框架学习总结-使用Mybatis对表执行CRUD操作
使用MyBatis对表执行CRUD操作——基于XML的实现 1.创建(create)用户:在userMapper.xml文件中增加: <!-- 创建用户Create --> <ins ...
- hibernate框架学习笔记4:主键生成策略、对象状态
创建一个实体类: package domain; public class Customer { private Long cust_id; private String cust_name; pri ...
- SSM框架学习笔记_第1章_SpringIOC概述
第1章 SpringIOC概述 Spring是一个轻量级的控制反转(IOC)和面向切面(AOP)的容器框架. 1.1 控制反转IOC IOC(inversion of controller)是一种概念 ...
- j2ee开发之Spring2.5框架学习笔记
Spring 2.5框架学习笔记 1.是一个开源的控制反转IOC和面向切面AOP的容器框架 2.IOC控制反转 public class PersonServiceBean { private Per ...
随机推荐
- Gin框架快速入门
github地址: https://github.com/gin-gonic/gin 初体验 安装: $ go get -u github.com/gin-gonic/gin 简单实例: packag ...
- Python argparse参数管理学习笔记1
1.前言 最近尝试学习使用argparse进行参数管理,顺便改善一下我那丝毫都不专业的.简单粗暴的代码习惯. argparse模块可以让人轻松地编写用户友好地命令行接口,并且还能够自动生成帮助与使用手 ...
- 自定义Python版本ESL库访问FreeSWITCH
环境:CentOS 7.6_x64Python版本:3.9.12FreeSWITCH版本 :1.10.9 一.背景描述 ESL库是FreeSWITCH对外提供的接口,使用起来很方便,但该库是基于C语言 ...
- MySQL-(InnoDB)事务和锁
在事务并行处理背景下,不同的事务之间因数据共享的状态变化,存在着某种依赖/隔离影响.即事务隔离级别. 事务隔离级别,官网的解释在这里. InnoDB提供 SQL:1992 标准描述的所有四种事务隔离级 ...
- API网关:开源Apinto网关-上游服务篇(二)
功能介绍 服务发现是一种分布式系统中的关键技术,它能够帮助应用程序动态地发现和访问依赖的服务实例,解决了服务实例分布在不同节点上的问题.通过服务发现,应用程序可以快速找到需要调用的服务实例的位置和元数 ...
- Github 自动化部署
github action 自动化部署 一.创建github 账户 官方地址 点击进入 注册/登录 二.在项目目录下创建文件 .github\workflows固定不变 develop.yml文件名自 ...
- sklearn中的KFold简单介绍
这一部分主要讲解关于什么是K-foldCV(K折交叉验证),简单的使用一些案例进行分析,然后使用sklearn库函数中一些简单的案例进行分析. 在机器学习中,多数最主要的功能函数被封装到sklearn ...
- 文心一言 VS chatgpt (6)-- 算法导论2.3 1~2题
一.使用图 2-4作为模型,说明归并排序在数组 A=(3,41,52,26,38,57,9,49)上的操作. 文心一言: 使用图 2-4作为模型,说明归并排序在数组 A=(3,41,52,26,38, ...
- 2022-02-19:安装栅栏。 在一个二维的花园中,有一些用 (x, y) 坐标表示的树。由于安装费用十分昂贵,你的任务是先用最短的绳子围起所有的树。只有当所有的树都被绳子包围时,花园才能围好栅栏。
2022-02-19:安装栅栏. 在一个二维的花园中,有一些用 (x, y) 坐标表示的树.由于安装费用十分昂贵,你的任务是先用最短的绳子围起所有的树.只有当所有的树都被绳子包围时,花园才能围好栅栏. ...
- 2021-05-06:给定一个二维数组matrix, 你可以从任何位置出发,走向上下左右四个方向 。返回能走出来的最长的递增链长度。
2021-05-06:给定一个二维数组matrix, 你可以从任何位置出发,走向上下左右四个方向 .返回能走出来的最长的递增链长度. 福大大 答案2021-05-06: 自然智慧即可. 动态规划.二维 ...