框架音频整理:
1 .Strtus工作原理:
(1)Strtus本身是一个mvc框架,对底层的servlet进行了封装。Struts的前端是一个核心控制器。叫做StrutsPrepareAndExecuteFilter,
(2)这个核心控制器StrutsPrepareAndExecuteFilter是配置在web.xml文件中的,配置的所有请求都会通过web容器进入到strtus框架,
(3)从前端发来的请求request,request进来之后会调用ActionProxy(控制器的代理类),ActionProxy会通过一个ConfigurationManager(配置管理器)来读取strtus.xml,strtus.xml能够找到目标URL所对应的Action,这样的话,通过ActionInvocation来调用Action,
(4)在调用Action之前,如果配置了interseptor(方法拦截器)的话,先执行拦截,执行完之后,再调用Action,执行完方法之后,会返回一个resute,resute会映射到一个结果,这个结果可能是一个页面,也可能是另外一个action。这样的话,就作为response的结果返回给用户。
2.strtus串讲与面试1
【答案】
Strtus2和strtus1都是mvc框架,Struts1的Action依赖于Servlet API,而strtus2的Action完全就与servletAPI解耦,这种设计模式属于一种无侵入式的设计。
Strtus提供了诸多的拦截器,利用拦截器进行了AOP的编程,实现了诸如权限拦截,日志管理等功能。同时也提供了类型转换器,把一些特殊的参数请求转化为需要的类型。
2> Struts2提供了拦截器,利用拦截器可以进行AOP编程,实现如权限拦截等功能。
3> Strut2提供了类型转换器,我们可以把特殊的请求参数转换成需要的类型。在Struts1中,如果我们要实现同样的功能,就必须向Struts1的底层实现BeanUtil注册类型转换器才行。
4> Struts2提供支持多种表现层技术,如:JSP、Struts标签、freeMarker、Velocity等
5> Struts2的输入校验可以对指定方法进行校验,这也是通过strtus2底层的validation的拦截器,解决了Struts1长久之痛。
6> 提供了全局范围、包范围和Action范围的国际化资源文件管理实现
3 strtus开发时,都需要那些配置信息?
【答案】
首先,需要在web.xml文件中配置一下StrutsPrepareAndExecuteFilter这个核心控制器,这样的话,所有的请求都会通过web.xml文件指向到strtus框架中,这个filter也是strtus框架的总入口,通过filter-mapper映射将所有的请求进入到strtus框架。前提是,将strtus的核心jar包拷贝到web项目下边,在启动web的时候会进行加载strtus框架。
还有一个配置,strtus.xml文件的配置。
Strtus框架也是通过读取strtus.xml文件来找目标的Action来调取目标的方法。执行完方法之后会返回一个resute,resute返回的结果可能是一个页面也可能是一个Action,然后作为一个response来响应给用户。此外,strtus.xml文件可以配置interceptor拦截器,拦截器可以配置在某一个Action当中,让某个Action具有拦截功能。
4 我们是不是一定要继承action—support父类?
【答案】
action—support底层有一些方法和功能,包括验证校验,拦截器,错误打印一系列功能都是在action-support里面。一般开发控制器类的时候,需要继承这个action-support类,如果不继承,也可以实现相关功能,但是不继承的话,只是会实现一些基本的功能。
5 strtus工作原理和工作流程。
【答案】
strtus框架是一个优秀的mvc框架,集成了控制器,前端页面的一系列组件,前端它的一些标签,更好的结合了java和html的一些工作。
1)Strtus本身是一个mvc框架,对底层的servlet进行了封装。Struts的前端是一个核心控制器。叫做StrutsPrepareAndExecuteFilter,
(2)这个核心控制器StrutsPrepareAndExecuteFilter是配置在web.xml文件中的,配置的所有请求都会通过web容器进入到strtus框架,
(3)从前端发来的请求request,request进来之后会调用ActionProxy(控制器的代理类),ActionProxy会通过一个ConfigurationManager(配置管理器)来读取strtus.xml,strtus.xml能够找到目标URL所对应的Action,这样的话,通过ActionInvocation来调用Action,
(4)在调用Action之前,如果配置了interseptor(方法拦截器)的话,先执行拦截,执行完之后,再调用Action,执行完方法之后,会返回一个resute,resute会映射到一个结果,这个结果可能是一个页面,也可能是另外一个action。这样的话,就作为response的结果返回给用户。
6 strtus2的优势。
【答案】
Strtus2与底层的servletAPI进行了完完全全的解耦。不再依赖servlet提供的request,response。更加简单清晰的将mvc框架进行分层,清晰地展示了页面,Action一个衔接的过程。同时框架提供了强的功能,如校验,国际化,拦截器。
7 strtus的底层系统级配置文件都有哪些?都有什么作用?在项目开发的过程中,项目的配置文件和底层的配置文件有什么关系?
【答案】
默认配置,
Deauflt-properties:这是一个属性文件,里面的参数是以键值对的方式存放。可以修改。包括:扩展名,国际化,拦截器。等一系列的基础配置。
Strtus—deauflt.xml:这里面配置了一些框架层的配置,不能修改,只能引用。比如resute-type,拦截器。在开发strtus.xml的时候,用到一个package,就需要继承一个包struts-default,这个包在每个开发都要继承这个包,struts-default就存在Strtus—deauflt.xml这个配置文件中。
以上这两个文件都存在于strtus—croe的jar包,Deauflt-properties可以在我们的strtus.xml配置文件中的constant重写,修改,覆盖。
8 详细介绍一下constent中的相关配置,功能。
【答案】
Strrus.xml是strtus框架中最核心的配置,它里面有一个constant文件,它是用来定义声明系统级变量的。在底层默认配置Deauflt-properties定义的属性都可以在这里进行修改。比如。Action的扩展名通过给value重新赋值进行修改。
9 详细介绍一下strtus.xml文件中package的作用。
【答案】
作用:将包下的Action 进行分类。
每一个包都有一个name属性,这个要求全局唯一,name不能重复。
每一个包也有一个namespace属性,namespace是通过前端发过来的request请求的URL不同来限定的namespace,它会与当前下的action进行匹配。Namespace也要求全局唯一。
Package必须继承一个struts-default,如果不继承的话,就会缺失一些底层的功能。
10 详细介绍一下strtus.xml文件中Action的配置。
【答案】
Action存在于package的子目录下,Action首先具有一个name属性,这个name是配合package的namespace使用,用户请求的URL会根据namespace和action的name进行绑定,这样的话,URL就会找到这个Action,同一个package下,name不重复。
第二个属性,class属性,当前的action进入到了控制器内,必须声明一个类,这个类必须是全路径的,这个类必须继承action—support这个控制器类。
第三个属性,method属性。方法名。如果不写方法名的话,就会默认去当前的class内寻找excute()方法。如果method填写了一个方法名,就会去当前class类找这个method方法。
在配置action的返回结果的 时候,我们会配置一个resute,这个resute就是执行action之后返回的一个string类型的字符串,然后通过这个字符串的值去匹配resute的返回结果,这个结果可能会返回到一个页面或者一个action的名字。
11 详细说明一下,action的 resute都有那些类型?
【答案】
我们在开发resute的时候,在配置文件声明的时候,都会给result一个type,如果不给定的话,他会默认给定一个。
默认:<resute -type name=”dispatcher” class=”” 这个默认是跳转到一个页面
<resute -type name=”chain” class=””默认跳转到一个方法
<resute -type name=”redirect” class=”” 重定向到一个jsp页面,url会发生变化
<resute -type name=”redirectaction” class=”” 重定向到一个action方法
<resute -type name=”plainText” class=””返回一段源代码,返回的是一个文本。
12 解释一下,URL和action的映射流程和关系是什么样的?URL怎么找到action?
【答案】
我们用户在请求后台的一个action的时候,都会通过URL去访问,这个URL会结合当前的action所在的package的namespace进行访问,也就是说,URL第一层会访问nameapace,找到namespace后,它会找到namespace下边的action的name,与URL的二级请求信息进行匹配,这样的话,URL再查找某个action的时候,就是先找当前action所在的包下的namespace,然后再找到包下的action的name,如果匹配成功的话,就会调用action所对应的class和method,进行方法调用,这个过程,就是URL查找某个action的流程。
13解释一下,strtus的include标签是怎么用的?
【答案】
include标签是在strtus标签中引入另外一个strtus的配置文件的。
目的:通过include标签引入多个子的strtus配置文件。它的好处就是,我们在开发我们的
Action层的时候,可以将action,controller层把他们进行分类。比如:我们在开发一个大型项目的时候,它会有许多业务模块,ERP,ON,CRM等存在一个项目当中的时候,就需要不同的struts定义不同的子模块,那么我们就可以在总的
Strtus.xml文件中引入不同的子模块的配置文件,这样的话每个子模块的配置文件就相互独立出来。
15详细介绍一下,在strtus中,页面和controller之间的参数怎么传递?
【答案】
页面传递请求到action的时候,有两种方式:1 属性驱动:在action定义的属性,在页面中有同样名字的属性,它可以通过同名的属性将参数传递过来。在action中直接get这个属性就可以把参数传递过来,前提是,定义的属性必须一致。2 利用模型驱动,这要求我们再写action类的时候需要继承一个modeldriver这个接口,实现里面一个核心方法,getmodel,getmodel会返回一个模型,这个模型就是我们某个实体类的类型,我们声明模型的时候,在action里要形成一个成员变量,并且要初始化,new一个对象,这样我们在页面访问到后台的时候,给模型一个属性值,这样就把页面的参数传递过去了。模型会把属性自动匹配到模型当中(实体类)的属性,并且自动封装成一个对象出来,这样我们就会把页面的值拿到。这是页面请求的参数,把参数传递到后台。那后台怎么把数据传回去呢?1,
ServletActionContext.getrequest.setAttbut把参数传递回页面,这个返回的页面和我们之前的request.setAttbut是一样的。2 通过模型驱动把值传回页面。
16action里的通配符。
【答案】
17 介绍一下strtus的动态方法。
【答案】
我们在配置strtus时,可以不给定某个类具体的action,也就是某个action不给定具体的方法,这种情况下,我们在调用URL的时候,可以通过我们的action加上一个!给定方法名,
以这种方式来调用我们的目标方法,此时我们调用的这种方法,没有在strtus.xml配置文件里面配置,这完完全全时通过调用action类的时候,给定!加上我们的方法名,就实现了方法的动态调用了,在调用动态方法的时候,必须要开启一个底层的开关,我们需要在constant里面配置一个<constant name="struts.enable.DynamicMethodInvocation" value="true" />
Strtus2框架音频整理2:
1 strtus2 有哪些常用的标签?这些标签和传统的标签有什么区别?在开发的时候怎么去使用这些标签?应该注意哪些事项?
【答案】
Strtus标签结合简化了form表单和U显示的迭代,与Java程序融合集成更加的紧密,大部分都实现了HTML标签,简化了HTML的传统写法,首先我们在开发strtus标签的时候,需要在jsp页面引入一个taglib,(<%@taglib uri="/struts-tags" prefix="s" %>)通过jsp指令taglib,uri指定具体strtus具体的uri。这里面常用的标签更多的是体现在form表单,<S:form,form表单使我们HTML中常用到的form标签的封装,这里面的action,直接给一个具体的action不需要给classpath,textfileld是我们的输入标签,这个标签里面需要给一个name和label,label是我们显示标签的显示名,username中的name所指定的名称是我们strtus标签必须要给定的。CheckBox是复选框,redio是单选框,select,submit是我们的标签。特殊说明一下就是我们CheckBox,redio,list,select这些标签当中,我们有一个属性叫做list,list所给定的内容是我们通过OGNL表达式能够动态的使我们的下拉列表,复选框,单选框,形成不同的内容,动态生成的,这个使用的语言,就是我们Strtus所提供的OGNL表达式,这个可以是静态的写法,也可以是通过后端返回的结果在页面中循环显示,strtus标签的优势就是极大的简化了我们在写传统的HTML标签的时候所带来的繁琐,
<s:form action="login2">
<s:textfield label="用户名" name="username"/>
<s:password label="密码" name="password"/>
<s:submit label="提交"/> </s:form>
Hibernate框架音频整理1
1 先简述一下hibernate与jdbc的区别,hibernate有哪些优势和劣势?
【答案】
Jdbc每一次请求数据库访问的时候,都会创建一个connection,会创建一个PreparedStatement或者statement,通过结果集访问当前数据返回的结果,把它封装成一个目标对象或者一个集合,这个过程中 jdbc存在大量的冗余代码,代码量偏多,关于事务关联查询实现起来代码量更是很大,同时jdbc没有实现缓存的机制,而且jdbc在跨数据库查询得时候,由于jdbc是用传统的原生SQL语句去写的,针对于mysql,oracle数据库的时候,jdbc它写的SQL语句是对特定数据库进行的。也就是说,jdbc的平台移植性相对很薄弱。
Hibernate是完全的面向对象,持久化的一个框架,并且有一个ormapping的一个概念,它会把我们的数据库,Java类,数据库的表字段和Java类的属性一一映射。并且能够很好的管理我们的Java类与类之间的映射,比如一对一,一对多,多对一,多对多的这么一些概念,通过这些极大地减轻了开发数据库的一些功能,同时在数据库跨平台这一方面hibernate底层封装了多种数据库的实现,我们只需要简单的使用hibernate的上层应用的一些API和它提供的hql语言,可以更好的实现跨平台这个操作,这样我们基本上看不到数据库底层的一个具体的功能,我们从Mysql迁移到oracle,够可以实现平滑平滑的迁移到其他数据库。对我们的代码修改几乎为零,hibernate更好地让我们关注于对象类之间的关系,那这些类映射到数据库就是表的逻辑关系,因此我们在开发hibernate的时候,熟练它的配置,他的映射关系,同时它也提供了一级缓存和二级缓存,减轻我们数据库操作的压力,提升数据库访问的工作效率,这样极大的提升了在传统jdbc使用时面临的一些问题。
2 简述一些下hibernate都有哪些配置文件?和各个配置文件的作用。
【答案】
在hibernate中主要有两个配置文件,第一个文件是全局的配置文件,默认情况下,叫做hibernate.cfg.cml
这里面包括数据库连接,映射文件,底层的hibernate框架它的基础性的参数配置。同时这个配置文件会指向我们引用那些MAPPing映射文件,来把mapping映射文件加入到hibernate框架当中。第二个就是mapping映射文件,一般情况下,我们会把实体类的名称.mapping.xml这种形式来命名,这个文件当中,其实就是对应我们Java类当中的一个一个的具体实现类,这里面会配置一些但前class里的具体内容,对应数据库的表,我们的ID,当前属性的id,还有一些实体的配置,比如,我们Java类当中的成员变量,对应那个表的字段,这里的类型是Java的基本类型,同时还可以定义一些复杂的集合类,这些集合类是对应到我们的类之间的一对一,一对多,多对多,类似于这种关系,hibernate在当前的mapping映射文件中我们可以更好地把它映射出来。配置好mapping映射文件之后,我们可以在hibernate.cfg.xml 文件中把它引入进来,来让hibernate框架读取映射好的文件,读取Java类和数据库之间的映射关系,我们只需要hibernate提供的API来操作当前类可以实现数据库的操作。
3 简述一下hibernate在操作数据库的时候怎么操作数据库的表?
【答案】
Hibernate在底层提供了一个工具叫做,hbm2ddl,这个工具我们会在hibernate.hbm.xml进行配置,这里的配置项,我们可以通过配置一些不同的启动的属性 ,第一个,我们在启动项目的时候,去生成表,这时候我们会去判断,我们的映射文件是否和数据库是否匹配,如果存在我们没有创建的表他会自动到数据库当中通过映射文件把表创建出来,他会通过表与表的关系把类与类的关系也自动生成,这个就是hbm2ddl这个工具的作用,它是在我们hibernate全局配置文件当中进行声明的,它有几种不同的方式,另外一种方式就是在我们启动项目的时候,会自动把表删除,重新建表,这种建表的方式我们用的不是很多,我们一般情况下用的是updata更多一些,增量的对表和数据库进行同步,也就是我们在类中增加了一些映射文件,而数据库这时候还没有生成这些表,启动的时候就会把表进行相关的创建,这个创建,就是Configuration在连接完一个配置文件到数据库的时候,他会自动判断mapping映射文件和数据库的表是否一一对应。这个就是hibernate创建表的过程。我们把这个工程叫做正向工程,也就是通过我们的Java类生成数据库创建表的过程。
4 hibernate可不可以逆向工程,就是通过数据库把表生成Java对应的类,把配置文件和实体类动态生成?它是怎么实现的?
【答案】
正向工程和逆向工程正好是相对应的,正向工程就是把Java类通过配置文件动态的生成到数据库,创建表,这个过程就叫做正向工程,那反过来,通过数据库的表结构,通过数据库动态的 生成Java类和mapping.xml配置文件,这个工程叫做逆向工程,在Myeclipse中有相关的工具,可以把数据库生成到Java实体类和mapping映射文件,因为hibernate他会有不同的版本,这时候的逆向工程针对我们的Myeclipse工具的版本是有一定的要求的,这个过程也不是推荐必须做的,但是针对于我们已有的系统在迁移使用hibernate使用过程中,可能会面临一种问题,这种问题就是我们使用逆向工程工具把数据库表生成到实体类和映射文件,这时候可能会出现映射的精准度不够,要对生成的实体类和映射文件做一些修改,就可以达到跟数据库同步,在hibernate中建议使用正向工程,也就是通过Java实体类和mapping映射文件去创建数据库的表结构。
5 简述一下,我们在开发hibernate时候所用到的API,和简单的一个开发流程是什么样的。
【答案】
在开发hibernate,的时候,首先要导入一个jar包,这些jar包是hibernate为我们Java所提供的开大时所依赖的包,第一个包就是hibernate的核心包,我们在使用hibernate3.0版本的时候,就是hibernate3.jar。这是引用的第一个核心的jar包。第二个包我们会引进hibernate所依赖的一些辅助包。这些包就比如,c3p0数据源,commons,loging,connection,这是hibernate相关的增强包,还有就是我们的log4j,还有其他的mysql,connection,oracle相关的jar包。这些是我们连接数据库的驱动包,此外还有动态代理的包,把这些包统一的引入到项目工程下面,这些包在hibernate官方都有提供,我们直接导入到我们的项目当中即可。这是第一步,导入jar包。第二步,我们需要配置一个全局的hibernate.cfg.xml文件,这个文件,我们需要放置在当前的classpath下边,第三步,我们需要创建实体类和实体类所对应的Mapping映射文件,Mapping映射文件所需要定义的就是当前类和数据库的表,字段,和属性所对应的一个关系。还有的话,就是牵扯到关联关系的一些配置,把他们配置好,在mapping映射文件中进行配置,有了这三个配置,我们就可以进行hibernate的相关工作了。这里面使用到的API有Configuration,Configuration是hibernate读取相关的hibernate.cfg.xml文件的时候所需要的 配置文件类。我们把它叫做配置管理器,通过它来加载本地的xml配置文件,把它读到我们hibernate框架当中,第二步,创建sessionFactroy,通过sessionFactroy可以创建session,sesssionFactory就是由我们当前的Configuration读取完本地配置文件之后生成的session会话工厂,通过sessionFactory来创建session,在一个项目中一个sessionFactory只有一个实例,这个就是session工厂的概念。第三步,session就是我们hibernate对数据库的一次会话操作的一个具体会话,这和会话是由sessionFactory创建的,通过sessionFactory opensession就会打开一个新的session会话,通过session我们会调用save,调用delete,可以创建一个Criteria,通过session去操作所有的hibernate相关的增删改查的功能。第四步,就是Transaction,事务,这就要求我们在执行save,update,delete操作的时候,需要开启一个事务,由session.beginTransaction()来开启事务,由transaction.commit来进行提交事务,来完成当前操作与数据库的一个同步。这几个就是hibernate常用的几个核心类。
6 简述一下,hibernate开发时,对象的状态都有哪些?他们的跳转流程都是什么样子?
【答案】
在hibernate当中,对象有三种状态:分别是临时态,持久态,游离态。
临时态:还处在Java内存当中,还没有到hibernate的内存当中,这样我们在new出来一个对象的时候,此时它的状态就是临时状态,此时它还没有和session建立任何关联。
持久态:持久态就是我们的临时状态调用save()方法的时候,它会把当前的临时状态对象保存在我们的session的一级缓存中,也就是说保存在我们的session缓存中,一旦进入到session缓存中的对象,我们把它称为持久态对象。这个状态的对象其实还没有同步到数据库当中,他只是在hibernate的session当中已经开辟了一块内存区域,把对象存到session当中,还没有同步到数据库。我们所调用的一些API有哪些可以直接把对象放到缓存当中?第一个,我们把临时态的对象通过session.save()方法把它放到session缓存中,第二个我们通过session.get(User.class,id)一个对象,通过session创建一个查询,返回一个列表,这个过程中产生的对象都是持久化状态。持久化状态和数据库同步只差一个提交。这个就是持久化状态。
游离态:游离态就是对象进入到持久化状态之后,在提交事务完成之后,对象的持久化状态会变成游离状态。
在一级缓存存在的对象都是持久化对象,临时态只存在于Java内存当中,游离态就是对象已经存在数据库了,它的状态已经同步完,这时候称为游离态。
7 简述一下,hibernate当中针对于数据库表的主键生成策略有哪些?
【答案】
我们都知道,在数据库的表在设计的时候,它是应该没有具体的物理意义和业务逻辑的,它主要是针对数据库当中每一行数据都有唯一的一个主键,这个主键我们通过唯一的一个数值能够找到记录。这个称为主键。在hibernate当中,提供了一系列的主键生成策略。这些策略都是跨平台数据库的,有些策略是不同的数据库它的支持是不一样的,这里有具体的几种实现方式:第一种叫做Increment,Increment是由框架自身生成的,也就是说我们在mapping映射文件当中,针对于类的id定义好之后的话,它都有个generator,它的class等于Increment的时候,hibernate框架会自动生成。这个生成的话,hibernate底层就会多生成一条语句,它会去当前表查找最大的id值,并把它返回到我们的hibernate框架,返回到对象,在我们save对象的时候,这个值就会自动的到数据库当中把最大id读取回来写到我们的对象当中,在我们sava对象到数据库的时候,这个id值就已经出现了,这个Increment是由hibernate框架多了一条自动查询ID最大值这么一个语句来生成的,第二个,叫做Identity,Identity是由我们数据库来生成的,也就是我们配置了ID的class,在generator中class=identity的时候,hibernate框架不需要关心id怎么生成的,在调用数据库的时候,数据库自动把主键生成,例如在mysql数据库中,我们如果给数据库的id设置成了自增这个属性,我们在使用hibernate的时候,就可以使用identity,在hibernate框架中对id不进行任何赋值操作,由数据库对id进行操作。第三个,assigned,assigned是我们程序来生成的id,框架不会进行id的生成,数据库也不会进行id的创建,由我们程序自动来生成。这种使用场景并不是很多。第四种,UUID。UUID是hibernate框架自己生成的string的字符串,这个要求我们当前ID必须是string类型的,这个时候hibernate框架会生成一个128bit的通过UUID算法来生成的一个字符串,这个字符串在任何时间,任何系统生成的id都是唯一的,这个字段的长度相对来说比较长,我们在创建主键的时候,不需要数据库来给,不需要程序来给,我们配置了UUID,hibernate框架会自动把值赋进来,返回的ID的值是varchar类型,这个UUID就是个string类型。最常用的就是Increment,identity,UUID这三种主键生成策略。
Hibernate串讲与面试2
1 在hibernate中怎么实现一个一对多的单项关联?
【答案】
一对多的单项关联说明的意思就是由一的一端找多的一端,例如公司与员工,一个公司对应多个员工,多个员工公用一个公司,一对多就是由公司去维护员工这么一个过程,在公司这个实体类里面对应多个员工这么一个关系,在公司company这个实体类里增加员工employee set, 这是在实体类的配置,在hibernate-mapping中company.hbm.xml我们需要针对于员工的set集合进行设定,首先得有一个set属性指向当前的实体类所对应的set属性。这里面会有一个key,这个key就是我们需要关联的多的一方的外键,也就是,公司这一方是父表,雇员一方是子表,我们在公司的.hbm.xml所设定的key,其实就是雇员的一个外键,由雇员的ID指向公司的id,但是在雇员的实体类里面是找不到对应关系和公司关联的,这就是一对多的单项关联。在set集合里面除了要配置key之后还要配置one-to-many,来指定class,这个class就需要指向对应多的员工的全局类名。这就是单项一对多的过程。在单项一对多的开发过程中,我们一旦将配置文件写好之后,我们对公司进行修改删除的话,都可以对雇员进行单项的操作,例如在公司新增加一个雇员,对公司雇员进行修改删除,这些信息都是对公司单项查找雇员的过程一对多的关联关系产生的具体的功能。
2 简述一下多对一的单项关联。
【答案】
我们知道,公司对员工是一对多,员工对公司就是多对一的关系。多对一就是我们通过雇员找公司,这样公司的类和公司的对应关系是不需要体现任何的一个属性,我们只需要在雇员的类里添加一个公司的属性,这样我们需要在雇员的类里添加一个company成员变量,第二步,在employee.bhm.xml中配置一个many-to-one的一个属性来指向company成员变量,给定一个class,叫做company,这里面需要一个属性叫做column,这个column其实指向的是当前雇员表的一个外键,这个外键指向了公司的id。有了这个过程,我们在开发多对一,单项关联的时候,我们就可以通过维护雇员的这么一个关系,来对公司进行维护,一般情况下,都是以查询的方式出现,因为我们在创建雇员的时候,公司就已经出现了,对雇员进行修改删除的时候,我们只是维护了雇员和公司的一个关系,这就是多对一的单项关联。
3 简述一下一对多的双向关联。
【答案】
一对多的双向关联就是把一对多的单项和多对一的单项全部都配置到两边的对象当中即可。第一个,需要在公司的实体类里面配置一个雇员集合,同时在company.hbm.xml中配置一个set集合,除此之外,还需要在雇员的实体类里添加一个公司的成员变量,还要在employee.hbm.xml中配置一个many-yo-one的属性,这样的话来实现一对多的双向关联,双向关联就是我从公司来维护雇员,也能从雇员维护公司,这种双向关联是最常用的,最普遍的。
4 简述一下多对多的关联。
【答案】
多对多的关系就是在两个对象中,都有对方的一个集合,比如,学生和课程,一个学生可以选择多门课程,一门课程可以供多个学生来选择。多对多的关系,在我们没有hibernate框架的时候,肯定会是有个中间表,这个中间表存放了两个字段,一个就是学生的id,另一个就是课程的id,在这个中间表当中,去把学生和课程的多对多的关系通过字段多读多的映射实现这种关系。在hibernate框架中我们只需要配置一些相关的实体类和映射关系即可,首先我们需要在课程这个实体类中定义一个set集合,来指定我们的学生列表,在课程的hbm.cml当中配置一个set集合,这里面需要给一个table,指向中间表,这里面的key指向的是当前课程和中间表关联的外键,这个外键存在于中间表 当中,同时还要设定一个many-to-many的属性,让它来指向我们所对应的多对多的关系是跟哪一个类进行多对多关系的,这里的many-to-many的column就是另外一端所对应的student的id,这是课程这边的相关配置,反过来学生那边的配置和这个是相互对称的,同样,在学生的类里面需要配置一个课程的set集合,指定我们的课程列表,在学生的额bhm.cml配置文件中需要配置一个set集合,指定它的name为学生类里面的哪个课程的集合属性,table也是指向中间表,key指的是当前学生类和中间表的关联的外键,此外还有一个many-to-many,让它关联对方的表,也就是课程表,column对应的就为课程的id。多对多也是常用到的业务场景。多对多的关系维护起来是对等的。
5 简述一下什么是hibernate的延迟加载?延迟加载的作用是什么?什么情况下使用延迟加载?
【答案】
延迟加载是在hibernate关联查询一对多,多对多的时候,Hibernate在加载对象的时候,只加载主要对象。关联对象暂不加载,使用时才去加载。也就是说,在关联查询的时候会出现延迟加载,在主体查询得时候,是否同步的将子表一起查询出来,如果能一起查询出来就是非延迟加载,如果在查询的时候,没有查询出来,在需要的时候我们再去查询他,这个时候,就叫做延迟加载,比如,我们在查询公司,查询员工列表的时候,如果我们开启了延迟加载,lazy=true,那么,我们在读取公司的时候,company中的employee set这个集合是不出现的,不会查询到数据的,我们只有调取到了公司的get employee set获取到它的子表得数据的时候,再到数据库去查询,这个就是延迟加载,延迟加载一般配置到我们关联查询的set集合当中,这时候如果我们设置成了延迟加载,它会更大的减轻我们在第一次查询的时候的整体查询性能,因为我们在查询公司的时候,可能不会牵扯到雇员,在需要查询雇员的时候我们再去加载它,在去到数据库查询,这个时候延迟加载会大大减轻数据库的压力,提升性能和效率。这是延迟加载整体的一个功能和使用场景。
Hibernate串讲与面试3
1 简述一下什么是hibernate的一级缓存。
【答案】
Hibernate的一级缓存也叫做session级别的缓存,是hibernate提供的关于session操作对象时产生的内存维护的一块空间,内存区域。叫做一级缓存。在一级缓存中存在的对象都是持久化状态,无需任何配置,hibernate都会自动支持一级缓存的。这是hibernate框架的最大的一个特性。也就是我们对当前的对象进行操作的的时候,session都会开辟一个内存空间,来存储我们的操作对象。这时候我们会通过调用session.save(),get,Criteria,query等一系列的查询,把对象放到我们的缓存当中,session缓存保存的对象的状态就是持久化的状态,存放在session中的对象只需要我们commit提交事务就可以把数据同步到数据库当中,持久化状态也叫做待命状态,这就是session的一级缓存。
2 简述一下hibernate的二级缓存。
【答案】
Hibernate的二级缓存也叫做sessionFactory级别的缓存,SessionFactory的缓存我们会存放一些读取比较频繁的数据,更改比较频繁的数据我们不会把他放到sessionFactory缓存里面,因为更新比较频繁的话,可能会影响到我们相关的同步的策略和效率,二级缓存是我们框架的选配缓存,得需要我们hibernate的配置来实现,二级缓存是我们整个框架当中跨session级别的共享的内存区域,我们的二级缓存存放的数据在任何的一个session级别的一级缓存是可以读取到的,这个可以理解为全局性的。这个配置过程,第一步,我们需要配置hibernate.cfg.xml,有这么几个点:1,需要把当前的二级缓存打开,(需要配置缓存的供应商)需要把property属性的cacha.use_second_level_cacha设置为true,2,我们需要引入一个第三方的二级缓存的管理的一个内置框架,这里我们用的是ehcache-1.2.3.jar,通过引入ehcache,我们把sessionFactory这二级缓存存入ehcache框架当中,这个就是二级缓存当中的一个整体的配置。就是在hibernate.cfg.xml全局配置文件中,第二个配置我们要在当前的类当中,我们的二级缓存其实是以实体类为切入点,我们需要在mapping映射文件中来指定某一个实体类某一个mapping文件具有这么一个二级缓存的功能,比如我们对公司设定一个二级缓存的功能,就需要在公司的mapping映射文件当中class的属性下边给定一个cache,让它的usage=“read-only”这个就是只读式的缓存,这个缓存配置好之后,我们把公司读取到一级缓存的同时,它会常驻我们的二级缓存,在我们的其他的一级缓存当中,是可以共享我们的二级缓存数据的,这样就会大大的减轻了数据库读取数据的压力,一般情况下,二级缓存都是针对于读取比较频繁,数据更改频度较低,我们会使用二级缓存对它进行封装的。
3 hibernate的一级缓存和二级缓存有什么区别?
【答案】
一级缓存是session级别的缓存,这个缓存是框架自动来执行的,这个缓存在session关闭之后,hibernate就会把session的缓存完全的释放。二级缓存是sessionFactory级别的缓存,它是全局的缓存,只要是数据进入二级缓存,我们的session就会共享二级缓存的数据来进行读取,一级缓存先去二级缓存读取有没有相关数据,有的话则进行读取,没有的话,就会进入到数据库进行读取,这样就会减轻数据库的读取的压力。
4 简述一下hibernate查询数据库的几种语言方式。
【答案】
Hibernate查询数据库有三种方式,第一种,我们使用jdbc的原生态查询。使用jdbc的原生态SQL查询,我们的查询语句完完全全用标准的SQL语句,我们使用的mysql,oracle不同的数据库所写的查询语句是不一样的,他跟我们传统的jdbc是完全一样的,这时候我们会使用session.Criteria,sql query去生成一个jdbc的对象类,由他来执行原生态jdbc的查询,第二种,用Query进行查询,Query查询会通过hibernate本身提供的HQL语言来进行查询,我们可以通过session.createquery 创建一个查询对象,这里所用到的语言就是HQL语言,这个过程,我们所写的查询语言都是通过hibernate提供的QHL语法来进行编写的,hibernate会通过对于对象的关系映射到数据库的关系再把它生成SQL语句,把它执行到数据库当中。第三种查询,我们会通过查询条件的类,我们会通过session.createquery这么一个对象来创建,这个对象封装了我们一系列的条件查询语句的静态类,通过这些类我们声明一些相关的查询条件,这是三种不同的查询方式。Hibernate当中建议使用query方式和Criteria来进行查询,主推的就是用query方式,用HQL语言查询,这是hibernate官方提供的一个很强大的封装的查询语句,它是完全面相对象的查询方式,它的语法是类SQL的方式。
5 什么是内连接查询,左外连接查询,右外连接查询,他们有什么区别?
【答案】
内连接就是我们常用的自然连接,两个表关联的时候,我们通过某个ID相等来进行查询的时候就叫做内连接。我们也可以通过inner join关键字进行两个表的查询,左外连接和右外连接是相对应的,左外连接就是
select a.*,b.* from a left join b on a.id=b.parent_id
这两个表关联的时候,左外连接允许左侧的表为空的字段出现的数据,右外连接就是指允许右侧的表的相关数据为空的情况下,在结果集出现。
左外连接包含left join左表所有行,如果左表中某行在右表没有匹配,则结果中对应行右表的部分全部为空(NULL)
左连接是已左边表中的数据为基准,若左表有数据右表没有数据,则显示左表中的数据右表中的数据显示为空。
右联接是左向外联接的反向联接。将返回右表的所有行。如果右表的某行在左表中没有匹配行,则将为左表返回空值。
这个一般情况下就是,是否允许某些数据出现空值的情况下,出现在整个查询结果当中。
6 简述一下hibernate当中n+1的情况是怎么出现的?为什么会出现这种情况?怎么去规避?
【答案】
n+1其实指的是数据库执行n+1此操作,这种情况一般会在关联关系中产生的,举例来说,在一对多的情况下,我们在查找公司时,如果非延迟加载,lazy=false的情况下,在查询公司的时候,如果公司有十个员工,查询公司的时候会产生11条SQL语句,其中一条是查询公司的,另外10条是分别查询10个雇员的,这就是n+1的产生。这种情况我们通过抓取策略,我们在定义公司的set集合的时候,要给它一个属性,叫做fetch,fetch什么时候等于select,我们改为join,通过连接查询的方式,把这两条语句通过一条SQL语句把它返回回来。这样可以解决n+1的问题。可以减少数据库频繁的查询,缓解数据库压力。默认情况下,我们没有设定fetch属性的情况下,它都会进行n+1的查询,查询公司 的时候,都会执行10次查询,把员工查询出来,通过fetch=“join”就可以把11条数据变为1条SQL,链接查询把它返回来。
你也可以设定fetch="join",一次关联表全查出来,但失去了懒加载的特性。
7 简述一下HQL语言都有哪些基本的语法?这些语法怎么去实现相关的查询?
【答案】
Spring框架的串讲与面试1
1 先讲一下什么是spring,spring是干什么的,在开发中我们为何要用spring?
【答案】
J2EE:J2EE核心是一组技术规范与指南,其中所包含的各类组件、服务架构及技术层次,均有共同的标准及规格,让各种依循J2EE架构的不同平台之间,存在良好的兼容性,解决过去企业后端使用的信息产品彼此之间无法兼容,企业内部或外部难以互通的窘境。
EJB:EJB是sun的JavaEE服务器端组件模型,设计目标与核心应用是部署分布式应用程序。简单来说就是把已经编写好的程序(即:类)打包放在服务器上执行。它是j2EE的一部分。
在Spring框架之前,传统的企业级开发使用EJB技术。Ejb全称叫企业级java Bean。EJB是一个重量级框架,他需要依赖EJB容器。EJB项目有很多冗余代码,开发效率低下,不利于维护和扩展。EJB项目不利于测试
Spring是一个轻量级的开源的j2EE框架,spring抛弃了之前我们必须在企业级开发所依赖的EJB,spring只需要依赖于JVM,就可以运行起来的j2EE轻量级框架,spring能够为我们带来企业开发时所需要的方方面面,包括MVC,包括持久层,包括spring提供的一系列组件,包括JMS,包括缓存,事务管理等等一系列功能,这些功能包括了我们企业开发所用的一切功能,同时它的轻量级为我们在开发,测试等一些特定的功能提供很好地支持,同时它的两个核心功能,一个是IOC,一个是AOP,这两个概念让我们在面向对象和面向切面有着很高的高度,这个就是spring框架为我们带来更好地优势。企业要用spring做的一个集成,和一些方方面面的模块开发,带来了更高的效率,同时让代码的清晰度,代码的完整性,和由容器管理功能达到了一个很好地条件,这时候我们用spring能够开发我们Java领域中几乎所有的项目,他可以作为整个框架中起到衔接作用的一个桥梁,能够把springMVC,strtus,mybitas,hibernate甚至其他的一些开源框架,mavencatch,mongodb等一些项目全部都集成到spring当中,这样的话,由spring管理整个框架,实现了一个优良的架构。
2 简单介绍一下什么是IOC。
【答案】
Ioc是控制反转。控制反转就是,我们之前对程序,对对象的控制,对象的声明,由原来的代码中抽象出来,放到我们的IOC容器当中,由spring的IOC容器对我们的对象的生命周期进行管理,这个过程就叫做控制反转,之前我们在声明一个对象的时候,我们都是通过new在Java对象中声明一个内存区域,来使用这个对象,以及这个对象的方法。我们如果通过IOC容器来做的话,我们只需要在容器中声明这个bean,这个实体类,我们就可以通过容器来获取到这个类的实例。这样的话不仅可以减轻创建对象过程中产生一些额外的工作,更重要的是,通过IOC可以实现我们Java代码之间的一个很好地解耦的过程,可以实现面向接口编程,也就是我们在容器中声明了一个接口,它的实例方法实例类由不同的实现类来做,这样的话,由容器来管理对象之间的耦合关系,这个过程大大减少了我们之前在Java代码中对象类型的一个强耦合的过程,这个是IOC最核心的概念。此外,IOC也起到了在容器当中管理对象之间的相互的依赖关系。这样我们在springMVC容器当中,可以更好的去集成不同框架当中所提供的业务bean,把这些bean放到spring容器当中,我们在开发框架当中,所使用的任何第三方组件放到IOC容器之后,我们就可以通过容器去获取所提供对象的实例,这样的话,大大降低了我们的代码和第三方代码之间的耦合性,把他们的耦合关系和关联关系全部交给容器来处理。
3说明一下DI,di的作用是什么?
【答案】
DI就是依赖注入,依赖注入和控制反转其实说明的是一个意思。依赖注入的意思就是,将我们程序中的依赖关系注入到容器中,由容器来管理他们之间的依赖关系,这个过程交给容器之后,我们不需要关注一些强耦合的关系,这时候需要容器去管理他们,因为通过容器管理可以更好地降低程序之间的耦合度,这样的话,springIOC底层为我们提供了更好的依赖管理,我们配置到容器当中的bean,他们就具有一些依赖关系,只需要出现在容器当中,我们不需要在对象代码当中进行管理,这个就是依赖注入的核心点。例如我们在spring框架当中集成hibernate的时候,hibernate有几个业务类:1.hibernate的Configuration 2.hibernate的sessionFactory 这两个实体类在Java代码中是不需要引用的,只需要获取一个session就行,
那我们在IOC容器配置一个session,它依赖与sessionFactory,再依赖于configuration,这样的话,sessionFactory和Configuration只需要出现在容器当中,他们的依赖关系产生在容器当中,我们只需要通过容器获取一个session就可以达到我们对访问数据库的会话的获取。这样ssessionFactory和Configuration的底层的依赖关系就会在容器中体现出来。这就是di的主要的体现方式。
4 介绍一下spring的基本配置都有什么?各自的作用是什么?一般的Java开发流程是什么?
【答案】
Spring为我们Java开发提供了一系列的jar包,我们可以通过官网去下载,这些jar包有AOP的,有ORM的,有context的,有web的,有bean的,等等一系列组件,首先在项目当中先引入组件,这些组件所对应的jar包都是不同的,我们需要哪些jar包,把它导入项目即可,这些都是以插件化的形式引到当前工程的,这里面会有一些核心的包,如spring—core,bean,context等核心包是需要引入到我们的工程中去的,spring有一个最核心的配置文件,一般情况下我们会把他命名为APPlicationContext.xml,这个配置文件的名称是可以变化的,我们在项目启动的时候会加载这个.xml文件,在容器当中,我们去定义一些bean的管理,在ApplicationContext.xml中进行相关配置,配置完成之后,我们就可以通过相关代码去获取到容器中实例的一些类。总结起来就是,我们在开发spring项目的时候,首先要导入spring的jar包,第二个,我们要有spring的核心的配置文件,这个配置文件中声明了当前定义的一些bean,一些实体类,还需要定义了一些相关的spring的配置,这些配置声明了spring的特性,通过一些相关的程序进行相关的集成。
5 简述一下,在spring的ico容器中实例化bean有几种方法?
【答案】
第一种方法:通过构造方法来实例化。我们在定义bean的时候,可以给它生成一个构造方法,可以是有参方法,也可以是无参方法,在一般的默认方法都是通过无参的构造方法来进行声明的,无参构造方法默认情况下,不需要特殊声明的,就可以在容器中进行使用,直接获取当前容器的实例,有参构造方法的话,我们是需要指定当前的构造方法的一个入参,通过入参给定值。这样的话,我们在ico容器中指定bean的具体的构造方法来把入参传递进来,就可以通过指定的有参构造方法来实例化当前的实例。另外一种方法是通过工厂模式来实例化,具体的有两种,第一种,静态工厂实例化,第二种,实例工厂实例化。这两种方法是又有不同之处的,静态工厂实例化是需要我们在定义bean的时候给它一个factory—method指定一个当前的工厂类的方法。这就是静态工厂实例化。实例工厂实例化很显然,就是这个工厂必须就是实例化之后,这个对象这个类,必须是非静态化的一个方法,这个过程就叫做实例工厂。通过实例之后的一个工厂,去创建实例,去调用实例的方法。两个的区别就是,一个调用静态方法,一个调用非静态方法。
6 简单介绍一下,bean的scope有几种类型?
【答案】
第一种类型,bean的scope作用域为单例。(Scope = singleton)Spring默认采用单例模式。单例的概念就是,在容器当中,实例化这个对象之后,这个对象的实例只有一份。也就是在IOC容器中只有一个对象,只有一份实例。那我们所有的引用到容器去获取这个对象的时候,都是调用这么一个实例去进行相关的方法调用。这就是单例。
第二种类型就是多例(scope="prototype")了。也叫做原型。原型模式就是我们每次从容器中获取当前bean实例的时候,都是生成一个新的对象,这个对象就相当于我们new出来的一个对象,每一次调用的对象都是不一样的,这样的话,我们在多个bean实例当中,他们的实体对象都是不相同的,也就是说,他们的实例化对象是多个对象,或是新的对象,这就是bean的多例化。
一般情况下,我们在写我们的spring,service层,dao层的时候,把我们公用的部分不写到类级别里面,写到方法级别里面,把它比拟成单例模式,我们在写Action,controller层的时候,为了保证每次请求的数据都是独立的,我们采用原型,也就是多例模式。
7 简述一下spring都有哪些模块组成?
【答案】
Spring提供的模块非常多,包括spring—croe,bean,context这三个核心模块,
expression(表达式),jdbc,orm;这是数据库方面的,
包括jms为Java的消息与服务。Transaction为事务管理。
接下来就是web模块:servlet,strtus,springMVC都有集成。
除此之外,第三方框架对spring进行集成。我们在用第三方框架的时候,spring本身没有提供集成,这时候我们可以看第三方框架自身是否提供集成,如果提供了,就可以将该框架集成到spring中。
8 spring核心配置文件中都有哪些配置信息?都包含哪些功能?
【答案】
Spring的核心配置文件applicationcontext.xml当中,首先我们需要引入一个头文件,这个头文件里面定义了我们当前需要一些模块的xsd的引入。通过这个xsd的引入可以把当前的配置文件关联到我们具体的某个模块上,比如bean,context,aop,等配置。这就是头文件。
第二个,配置一些spring的全局配置。包括启动的注解驱动,通过组件扫描,配置bean,配置别名,甚至配置事务管理器,aop等等都是在核心配置文件里配置。这个核心配置文件时spring工作时的基本骨架,我们所有的内容都是根据这个配置文件来做的。
9 简述一下springIOC容器的手工注入和注解方式有什么不同?
【答案】
手工注入:就是通过配置文件applicationcontext.xml进行注入,在配置文件里声明式的去声明一些bean,
把这些bean的ID,class的相关属性,相关方法等进行声明,这样的话,我们可以通过容器来获取,bean声明的一些具体的实例,这是第一种方式,手工注入。
注解注入:什么叫注解,我们通过容器的两种行为,第一个是写入容器,第二个是从容器里读取,通过.xml的形式,手工方式呢,就是在容器中定义了这个bean,我们只需要在容器你中去get就行了,另外呢,通过注解方式的话,首先要把注解驱动打开,把组件扫描打开,这个过程中我们不需要在.xml文件中声明,只需要在类的上面添加相关注解即可。在开发的过程中,需要用到controller,service,Repository ,Component等注解,我们只需要告诉当前类,需要声明成那种组件,给定一个名称,它就会自动的扫描的方式进入到 ico容器,IOC容器就能够在类层面识别到某一些注解的类并且在IOC容器中实例化,我们在get的时候可以通过resource,autowire这么一个引用的方式把类从容器当中拿出来实例化,这就是通过注解方式来完成的,在开发的过程中,手工注入和注解注入应用在不同场合,一般来说,我们在配置一些固定的框架的时候,通过手工注入在.xml文件中进行声明,这样更有助于我们配置框架,更加清晰的看到我们配置的内容是什么,我们自行写的service,dao层,controller等组件是通过注解的方式来声明的,通过resouce,autowire来通过容器读取。这是两种不同的方式,在开发时,注解注入的方式是用的最多的。
@Repository 这个注解会告诉Spring,具有该注解的类是一个Dao对象。
@Service这个注解会告诉Spring,具有该注解的类是一个Service对象。
@Controller这个注解会告诉Spring,具有该注解的类是一个控制器对象。
@Component这个注解会告诉Spring,具有该注解的类是一个Bean对象。(这个注解一般用于对Util类进行注解)
Spring框架的串讲与面试2
1 简述一下什么是spring的AOP,它的原理是什么?
【答案】
AOP是面向切面的编程,可以说是OOP(面向对象编程)的补充和完善。面向对象一般都是基于面向过程,面向对象的程序过程为技术点,面向切面是利用了程序交叉横切的这个技术,来将多个类的公共部分,公有的一个代码块抽象出来,定义为一个切面aspects,将这个切面我们以业务模块其他一些不同的业务方法当中的逻辑是完全分离的,这样的话,我们把一些核心的通用的功能放到切面当中,减少系统代码的重复,降低了模块之间的耦合性,并且对未来的可扩展性和维护性都有很好的性能,这就是AOP的一个整体的概念,AOP在更多的使用场景,包括权限,缓存,日记,包括事务管理等一系列,都使用AOP技术,在框架中单独处理一些特有的与其他业务不相关的业务,这样的话,AOP就大大的减轻了程序和公用模块代码之间的融合性,在spring中提供了非常全面的AOP的技术,我们可以用IOC容器管理模式来管理它,这样的类似的概念我们之前也遇到过,例如之前web当中的fiter,strtus当中的Interceptor,都是AOP很好的典型例子 。
2 简要说明一下spring的AOP的开发流程,都涵盖哪些具体链接,具体工作。
【答案】
第一步,AOP是面向切面的,它的切面的切入点都在现有的业务方法中产生,这时候我们就需要确定一个目标,对那些类的哪些方法进行切面植入,就比如说我们要实现一个事务管理,我们需要对哪一些业务方法进行切面的开发植入,这就是我们的第一步工作。
第二步,需要我们在IOC容器中声明一个切入点,这个切入点指的就是当前所要找的一个目标类的具体切入过程。假设我们要实现所有service方法的一个事务管理的切入,我们就需要spring提供的AOP point—cut来提供一个expression来给定一个表达式,这里面会通过一个灵活的写法来涵盖那些目录下边的哪些包下的哪些方法进行切面植入。目的是找到的一个目标的执行的切入点。
第三步,定义一个切面,这里的切面指的是我们切入之后所要执行的公共方法,这个过程需要我们在IOC容器中定义一个bean,让它来去执行我们当前的切入点当中要执行的公共方法的植入。这是定义了一个切面,切面需要在IOC容器当中定义一个aop aspects,会指向到我们的切面,同时会给一些通知,这些通知是一些核心的概念,这些通知会在我们调用目标方法之前,之后,或者之前之后都执行等这么一些通知,来满足植入的目标方法,这就是整体的一些方法和步骤。
3 说明一下AOP当中的advice都有哪些类型?
【答案】
第一个,前置通知,叫做before。是调用目标方法之前执行的通知。
第二个,后置通知。after-returning。是调用目标方法之后执行我们的切面的通知。
第三个,around比较重要的一个通知,叫做环绕通知。Around。目标方法调用之前进入切面连接点方法,如果在 连接点中没有调用proceed()方法,则它不会执行目标方法,如果调用了proceed方法,它才会进入到目标方法,最后会返回到切面的方法。环绕通知和前置,后置通知最大的一个区别就是:它能够控制程序的目标方法是否执行,就类似与之前strtus中的拦截器,如果拦截器invoke放行之后,会执行目标方法,如果没有放行的话,它是不会继续执行党的。环绕通知和拦截器相类似,我们在进入目标方法之前,可以通过切面的程序来控制是否进入目标方法,这样我们就可以死通过环绕通知来实现。
以上三种通知类型为最常用的类型。
注:环绕通知 ProceedingJoinPoint 执行proceed方法的作用是让目标方法执行,这也是环绕通知和前置、后置通知方法的一个最大区别。简单理解,环绕通知=前置+目标方法执行+后置通知,proceed方法就是用于启动目标方法执行的
4 简单的举个案例,说明AOP的开发流程,来实现service层的日志管理。
【答案】
我们的目标方法是需要给service层添加一个日志,这个日志是打印当前的service层的方法调用,调用的某个方法,调用的时间,这里面我们要使用log4j,我们是需要 建立一个切面,这个切面会切入到整个service的方法当中,这样所有的service类,所有 的service方法都会执行这个目标切面,首先,我们需要确定我们执行哪些service方法,如果是所有的service方法,我们就需要建立一个AOP pointcut在.xml中进行声明,给定一个expression(表达式),让它去指定到某一个目录下的所有方法,来进行一个切面的切入点的定义,其次,我们要声明一个bean类,这个bean类是我们切入点切完后进入到我们切面的目标方法,要执行的一个具体的日志方法,这个日志我们要建一个bean,叫做logbean,logbean里面有一个目标方法,叫做log(),定义好bean之后,我们需要finally,在.xml 中声明一个 aspect 指向当前的log,同时在当前的AOP当中,配置一个前置通知,证明方法已经进入,把前置通知pointcut—ref指向我们所声明的切入点,这个aspect需要指向当前切面的类,也就是log bean,配置好之后,我们通过调用每一个service方法,都会进入到我们的切面类,执行我们的log方法,来为我们每一个service层的方法进行调用和打印,这样的话就减少了每一个service层都要调用log,log4j的方法,去打印日志。
5 简要说明spring对ORM的支持。和JDBC的支持。
【答案】
Spring提供了对JDBC的相关支持,spring提供了对JDBCTamplate的工具类,我们只需要在IOC容器中引入相关配置即可。流程如下:第一步,想引入JDBCtamplate这个工具类,来对jdbc原生态的一些操作,先要引入相关jar包:Spring-jdbc-版本号,引入数据库驱动等。第二步,需要在系统中配置一个properties的文件来使用,这是对数据库的一个配置,声明。第三步,需要配置一个数据源,这个数据源只要是标准的Java官方的或者第三方的都行,比如c3p0,DBCP等。把它引入到我们的bean容器中进行配置,把它引入到IOC容器当中,我们需要在bean声明一下,jdbcTemplate,它的class指向jdbcTemplate,这个property里面有一个DataSource,指向我们在IOC容器声明的即可。在jdbcTemplate当中使用了非常多的底层封装的工具类,包括预编译,增删改查等方法的封装,我们直接用jdbcTemplate使用就行了,不需用去关心一些数据库连接的一些事情。因为这些已经被IOC容器封装了。Hibernate也是一样的,提供了hibernateTamplate工具类,这些都是spring对JDBC,对hibernate的一些相关的支持。只需要对框架进行简单的配置,就可以把这些工具使用起来。
6 简要说明一下,Spring怎么对事务进行管理?(需要重新整理)
【答案】
Spring提供了针对service层进行统一管理的管理模块,首先我们需要引入一个tx组件。
引入完之后,需要在IOC容器当中声明一个tx-advice来指明我们的事务管理器,这里我们定义了method,每一个method都有一些不同的事务处理,
7介绍一下spring 事务的传播行为。
【答案】
我们在写框架的时候,在service层,我们可能会调用多个dao层,那这个时候,我们怎么控制事务,事务都有相互调用的这么一个过程,要处理这个问题,首先来看几个属性的概念,事务嵌套,怎么处理?这个就是spring事务传播的一个行为。首先,第一个,require,require就是业务方法在一个容器里进行,如果方法运行时,已经处在一个事务中,那么久加入到这个事务当中,否则自己新建一个事务。也就是在sevice中,有一个业务方法调用了另外一个dao层,它会有两个事务,第二个事务进来之后,就会在当前的事务体系当中,来进行一个统一的管理,这样的话,相当于以主方法调用方法为主去做统一的管理,这叫做require。第二个,叫做,not-support声明方法不需要事务,这个就是如果一个方法没有关联到一个事务,容器则不会为它开启事务,如果方法在一个 事务中被调用,该事务会被挂起,结束。这个过程在我们管理事物的时候一般不会用到。一般情况下,我们都会使用required,也就是说,在嵌套新的事物的时候,按照我当前的事务来走。这个过程比较常见。
SpringMVC框架的串讲与面试
介绍:springMVC框架是spring框架中发framework里面的一个轻量级的MVC框架。
1 strtus和springMVC有什么区别?
【答案】
第一个区别:strtus框架的入口为filter,而spring的入口为servlet。
第二个区别:springMVC与spring集成是天然耦合的,因为springMVC是spring框架中frameWork中的一个轻量级框架。
第三个区别:springMVC的配置成本是很低的,几乎实现零配置,而strtus的配置相对来说是比较高的,通过相关配置来实现相关的工作。
第四个区别:springMVC的开发性能是远远高于strtus2。
2,介绍一下springMVC的核心工作原理。
【答案】.
工作原理:前端的request请求到达web项目当中,首先通过web.xml当中映射的DispatcherServlet,通过映射所有的URL请求,把它转发到springMVC的DispatcherServlet核心控制器,这样的话请求就会进入到springMVC框架,然后DispatcherServlet会把请求路由到springMVC的HandlerMapping,通过springMVC配置的controller和URL映射的关系会查找到具体的某个controller,找到这个controller之后,DispatcherServlet就会通过HandlerMapping的适配器找到controller方法和类,就会进入到执行方法,执行完这个方法之后,controller方法就会返回一个modleandview的一个对象,返回之后springMVC框架会通过视图解析器将返回的modleandview中的view进行解析适配,找到目标的视图,将结果返回页面进行渲染。整个流程就执行完成。
3 怎么在web.xml中配置springMVC的核心控制器?
【答案】
SpringMVC和web容器进行融合的时候,需要在web.xml 中配置一个servlet,配置servlet的servlet-name我们可以指定,它的class需要指定DispatcherServlet,并且需要通过init-param这个参数把当前我们springMVC的配置文件spring-servlet.xml配置到参数当中,在启动springMVC时候会加载此配置文件。并且需要映射当前Servlet所映射的url-pattern指向所有的请求。
4 如何配置视图解析器?
【答案】
视图解析器需要在springMVC的核心配置文件中进行配置,也就是在spring-servlet.xml中,配置的话需要指定一个视图解析器的实现类,叫做InternalResourceViewResolver,把它的两个属性进行设置,一个是prefix,前缀,指向的是jsp页面的目录。一个是suffix,后缀。指向jsp页面的扩展名。它的值是.jsp。只需要把这个bean配置完之后,springMVC就可以进行视图的解析。找到我们的jsp目录,找到.jsp文件,找到具体页面。
5 简单说明springMVC的注解有哪些?
【答案】
第一个注解,requestMapping,可以在类级别和方法上进行定义。累计别的注解,是URL的一级路径,方法级别的requestmapping是URL的二级路径。requestmapping配置的URL和前端的URL进行匹配,在一个项目当中,不允许出现重复的requestmapping映射的URL。否则启动服务器会报错。PathVariable是通过URL将请求当中的占位符绑定到URL传递过来的参数当中,可以通过控制器的方法作为入参进行绑定,一般会配合requestmapping进行使用,在requestmapping中指定通过一个{}的占位符去获取参数,在我们的方法当中,使用PathVariable指定一个具体的参数值。下一个常用注解,ResponseBody,这个注解的作用是将controller的方法返回的对象通过适当的转换器转换为适当的格式后,写入到response的Body区域,通常返回的结果是json,或者xml。那Ajax前端可以通过相关数据传递到后台的时候,我们就可以通过responseBody把我们的json格式或者xml格式返回到Ajax,一般情况下ResponseBody会搭配AJax来使用。
6 说明一下,springMVC怎么在页面和后台,controller之间进行参数的传递?
【答案】
参数的传递有两种,一种是页面往controller传值,另外一种就是controller返回的参数。先说一下怎么从页面传值到controller,有第一种方式,用原生态的servlet进行参数的传递,原生态的servlet我们可以在springMVC当中在控制器当中,可以写一个servlet,方法,方法的入参可以是HttpServletRequset和HttpServletresponse,这样我们可以用原生态的ruquset.getParameter 获取页面表单的属性,第二种树属性驱动,属性驱动要求在写form表单的时候,和我们controller对象当中的属性进行匹配,我们在input标签中的name和我们在controller方法的入参当中对象的属性名进行匹配,这样的话,我们在吧数据从页面传向后台的时候,springMVC会自动的把页面的属性西东封装成我们controller方法当中的对象,来进行参数的绑定,这就是属性驱动模式。 Controller返回参数到页面的时候,一般情况有这么几种方式,第一种,我们将modelandview作为controller的方法的返回值,将modelandview的model,模型数据封装进去,再将view视图封装进去,视图解析器就会解析到我们返回来的页面,并且把model的数据返回到页面进行渲染。
7 介绍一下springMVC的拦截器。
【答案】
SpringMVVC的拦截器自定义拦截器需要实现HandlerInterceptor接口,此接口需要实现三个方法,第一个方法是preHandle()也就是在进入controller的方法之前先进入该方法。该方法返回的类型为Boolean类型如果为true,则继续执行,如果为false,则停止执行不会进入到controller方法。第二个方法是postHandle(),这个方法在处理器处理完成之后,但是DispatcherServlet向客户端相应返回结果之前被调用,在该方法当中,用户请求request进行处理。第三个方法是afterCompletion()。这个方法是DispatcherServlet完全处理完请求之后被调用,可以在该方法中进行资源清理的操作,也就是说这三个方法是进入到controller的方法之前,过程,和之后整体来执行的。SpringMVC的拦截器主要是围绕controller的方法进行的,拦截的都是某个controller的方法。关于拦截器的配置需要在核心的spring-servlet.xml配置一个 <mvc:interceptor>指定我们需要拦截的URL,并且要指定URL所映射到的拦截器。
Mybatis框架串讲与面试
1 首先介绍一下Mybatis。
【答案】
Mybits是Apache下的开源项目,它是一个优秀的持久层框架,它对JDBC进行了轻量级的封装,使开发者只需要关注SQL语句本身,它将SQL语句和Java代码进行了分离,并且在注册驱动,创建数据库连接,statument等相关的配置当中,进行了封装,同时它将我们在jdbc的一些复杂的操作进行了抽象简化,能够让我们在mybits的配置文件当中实现复杂SQL的一些配置。
2 Mybits与jdbc的区别。
【答案】
Jdbc和Mybits没有可比性,mybits完全是在jdbc之上的,操作更加简单,代码更加简洁,有基础的应试能力,并且提供了持久层框架的全部功能。包括一级缓存,二级缓存等。
3 介绍一下Mybits和hibernate的区别。
【答案】
Hibernate是完全的面向对象,跨数据库平台,自动生成SQL语句映射文件的一个持久层框架。它的劣势是性能不够好,数据量大的时候存在性能问题,并且我们在进行自定义数据库脚本开发的时候,存在很多的不友好性。而Mybits属于轻量级的持久层框架,是非面向对象的持久层框架,它采用了原生态的SQL语句进行开发,可以更加灵活的实现不同的复杂数据库的语句的编写,它的劣势就是每一步操作都要写SQL语句,并且不支持数据库的跨平台。也就是我们在mysql。Oracle,SQL server等数据库进行数据库切换的时候,Mybits做不到很好的移植性,有一部分SQL语句我们需要重新编写。
4 介绍一下Mybits的配置文件都有哪些?
【答案】
同样,Mybits的配置文件有两个,第一个,SqlSessionFactoryconfig.xml他与hibernate的hibernate.cfg.cml文件类似的,都是进行全局的配置文件,包括配置数据库,映射文件的导入,其他的全局系统配置等等。另外一个就是mapper映射文件,mapper映射文件就是我们在Mybits当中与Java对象和数据库之间映射关系的配置文件,我们在里边进行每一个对象的数据库操作的脚本的编写,类之间的关系等等。
5 介绍一下SQLsessionFactory。
【答案】
在Mybits当中,SQLsessionFactory是一个全局的session工厂,用于创建SQLsession的,一般情况下,一个项目只有一个SQLsessionFactory实例。也就是说,它是单例模式,他需要通过一个InputStream输入流来去构建我们的session,输入流一般会通过我们读取我们的SQL配置文件来生成我们的当前SQLsession的builder,之后的话来实例化我们的SQLsessionFactory。
6 说明一下SQLSession的工作原理。
【答案】
在Mybits中的SQlsession和hibernate当中的session是极其类似的,SQlsession 是通过SQLsessionFactory来创建的,每次会话都会创建一个新的session,默认情况下,事务commit是false需要手工来提交。在SQLsession中会有Mybits常用的一些方法,如selectone,selectlist,selectmap,update,delete等常用的增删改查方法。
7 介绍一下resutetype和resutemap的区别。也就是在 配置文件中两个的属性。
【答案】
Resutetype是Mybits配置文件中的一个主要的返回结果类型,如果我们在select中配置了resutetype所指定了一个类,当前我们返回的SQL语句就需要把当前这个类型所对应的属性通过SQL语句的字段匹配,一个一个的进行封装,这时候我们指定的resutetype的类和数据库里字段必须要一一匹配。如果不匹配的话,在我们封装成resutetype这个对象的时候,在Mybits的Java对象当中,我们就拿不到当前实例的一个属性值。而resutemap需要我们在mapper映射文件中需要单独配置一个数据库和对象之间的一个映射关系,来将数据库字段和Java类的属性名称不匹配的属性映射,这样在select中,它返回的resutemap中指定我们定义好的mapper,这样的话在数据库字段和类属性名称不匹配的时候进行映射,这样就能实现数据库和对象的不一致的映射关系。而result的另外一个功能就是可以实现对象与对象,数据库表之间的一对多,多对一的映射关系进行配置。
8 介绍一下Mybits中的动态SQL。
【答案】
Mybits的动态SQL能够更好的支撑在运行CRUD的时候,能够进行动态的判断,它的语法与jstl类似。在当前的判断当中,与el表达式相类似,在sql当中,包括if判断,值得非空判断,有where判断,用where进行条件的匹配,还有set的标签,set标签在批量更新的时候使用的foreach标签是用在子查询的循环遍历判断当中来使用的。
9 介绍一下Mybits中一对多多对一的配置。
【答案】
先来说多对一,举例说明吧。User和company是多对一的关系。首先在user类里定义一个company的成员属性,同时要配置user的mapper.xml 文件,在user的xml文件里面要配置一个resultmap,在resultmap里面需要对user所关联的<association 定义,association 所定义的属性为company,我们在对user进行查询的时候,它的返回结果就可以用resultmap进行返回,这样就可以实现user和company之间多对一的关联查询,一对多的关系,比如用户user和简历Resume 之间,要实现这种一对多的关系,首先在user类中定义一个resumeset,这个属性,其次我们在user里面定义一个resutemap,通过resutemap里面的collection来去指定我们当前关联的resume,collection所定义的属性为resumeset,再把其他的resume的属性配进来,我们在对resume查询的时候,它的返回结果就可以用resultmap进行返回,这样就可以实现user和resume之一对多的关联查询。
10 讲述一下Mybits的一级缓存和二级缓存。
【答案】
Mybits的一级缓存就是sqlsession级别的缓存,与hibernate相似。Sqlsession是在每一次创建数据库会话的时候产生的一级缓存。同一个sqlsession当中,同样的查询,第一次读取数据库,进入缓存之后,第二次查询的时候,就不需要到数据库查询了,只需要在缓存中读取。二级缓存是sqlsessionFactory级别的缓存,我们需要在SqlSessionFactoryconfig.xml中把二级缓存打开,在settings中设置setting,CacheEnabled设置为true即可。第二个是在mapper映射文件中去指定我们当前的二级缓存的一个配置。<cache read-only=”flase”这就是二级缓存的一个基本配置。二级缓存当中,他是一个全局缓存,我们之前如果通过二级缓存查出来的数据如果再次查找的时候不管是在各个session当中,他都是可以跨各个session域来进行二级缓存的读取的。
常见工具与知识扩充 maven SVN Tomcat log4j
1 什么是maven,maven如何来使用?在Java开发中,maven具有哪些优势?
【答案】
Maven是阿帕奇下的一个开源项目,它是针对于我们当前项目的jar包依赖管理和项目管理的一个工具。我们一般使用它都是在eclipse下面集成maven工具来对项目开发进行管理,首先我们在生成maven项目的时候它的项目结构是不一样的,它会把Java的源代码,Java的测试类,Java的资源文件,xml文件,property文件,jsp文件会统一的按照maven的标准格式来创建,创建完之后,我们会看到有一个pom.xml文件,pom.xml是maven核心管理工具的配置文件,我们Java项目所依赖的所有的第三方jar包,都会通过这个配置文件进行依赖声明,通过添加一个dependency可以引入我们当前项目所需要的jar包,一旦我们通过pom.xml引进了jar包,maven在eclipse工具下就会自动的通过网络下载相关jar包,下载到本地的某个仓库,下载完之后,我们当前的项目就可以正常的使用jar包了,这样的话极大的减轻了在项目开发时寻找不同版本,不同jar包的各种jar包的时候,提供了一个非常好的管理工具。这是它的第一点,第二点呢,maven也可以对我们当前项目的构建管理提供一个很好的帮助,我们可以通过maven和eclipse的集成来把当前的Java工程和Javaweb工程打成jar包或者war包,打成war包之后,它就是我们目标运行的一个整体的jar包,我们可以把它部署在TomcatAPP下,这样我们在启动Tomcat的时候,Tomcat就会自动部署war包,生成一个文件,启动之后,这个项目就会运行起来,总体来说,maven是对我们的项目依赖管理提供了很好的帮助,极大的减轻了我们程序员在不同jar包之间寻找不同版本时,产生的极大的工作量。这就是maven带给我们的一个很好的优势。在一般情况下,在eclipse开发的时候,本地会指向到一个仓库,在我们下载完所需jar包之后,他都会存储到本地的仓库,在我们第二次,第三次多次创建本地项目工程时,我们只需要指向到 本地的仓库当中即可。这就是maven整体工作的一个流程。
2简述一下Tomcat,以及Tomcat的运行原理是什么?我们如何使用它?常用的一些命令脚本有哪些?
【答案】
Tomcat是Apache下面的一个最重要的web容器的开源项目,我们可以通过Apache官网下载不同版本的Tomcat,平台不一样,版本不一样。我们下载的通用版本,既可以运行在Windows平台,也可以运行在linux下边运行,它所具有的目录结构是统一的,它的运行脚本会发生变化,在Windows下的话,我们在启动Tomcat的时候,可以通过startup.bat这个执行文件,同样在关闭的时候,可以使用shutdown.bat来执行关闭Tomcat。在Linux系统下,启动Tomcat的时候,可以通过startup.sh来执行启动Tomcat,在关闭的时候,可以通过shutdown.sh来执行关闭Tomcat。Tomcat在整个目录结构下边有一个目录结构是非常重要的,叫做webapps,这个目录是我们把当前的web项目打成war包部署在webapps下边,当Tomcat启动的时候,他会自动将当前war包部署成目录结构,让Tomcat来运行当前的项目。这个就是Tomcat简单部署项目的过程,把war包扔在webapps下边,它就会自动部署。这个就是简单Tomcat的一个使用,除此之外,Tomcat还有一个核心的文件,叫做server.xml文件,这个实是在conf目录下边,这个文件配置了Tomcat所具有的端口号,编码格式等相关的高级配置,这些配置是我们在部署到生产环境之后,可能会用到的一些配置项目,我们可以修改server.xml来修改相关的配置信息。
3简单介绍一下log4j,开发过程中为什么要用log4j?Log4 j具有哪些优势?
【答案】
在开发项目当中,打印日志是我们最常用的一种功能需求,在项目运行的过程中,会产生一些业务数据,我们想看系统运行的情况和需要打印运行数据的时候,我们就会用到日志管理功能,log4j就是面向Java体系当中所使用到打印日志的一个基本框架,它是Apache下的开源项目,我们通过引入log4j的jar包,去使用log4j,引入log4j的jar包之后,我们需要在log4j所在项目当中创建一个log4j.properties的配置文件,在这个配置文件当中,我们来声明当前日志的打印级别,日志所存储的目录结构,放到哪个目录下面存储什么文件,这个是我们log4j文件的一个基本配置。那么在项目当中我们通过log4j提供的API来去使用它的功能,打印我们不同级别的日志,包括info级别的,包括error级别的,包括警告级别的,包括debug级别的这些级别,这些不同级别的日志级别是针对于不同产品来提供使用的。那log4j的级别越高,它的严重程度越大,从最常用的四种日志级别来看,error,warn,info,debug这四个级别是由高到低的,error级别最高,debug级别最低,级别最高的情况下,打印出来的日志最少,如果定义了error级别的日志打印,它只会打印error,如果定义了debug级别的日志打印,他就会把debug,info,warn都会打印出来。一般情况下,项目开发过程中,我们都设置成info级别的日志打印,在开发环境中,我们的日志级别是设置成debug级别的日志打印的。所以在开发环境中,设置成debug级别的日志打印,打印出来的数据是非常多的,那把它部署到生产环境中,正式环境中我们会把日志级别调高,比较低级的日志级别是不会打印出来的,这样的话,对我们产生的一些日志文件读写的频度会降低,对系统的压力会有所改善,这个就是log4j的使用的一个过程。Log4j在一般项目中都会使用到,比较关键的就是使用hibernate,在打印我们的SQL语句的时候,它会使用到log4j,mybatis也是一样的,在项目当中使用log4j是非常关键的一个步骤。
4简单介绍一下SVN,在项目当中怎么使用SVN,它常用的功能有哪些?
【答案】
SVN是一个版本管理工具,这个版本,在项目开发当中主要是对代码的一个版本。在项目开发当中,主要集成到eclipse当中,首先我们会在eclipse中安装一个插件,我们在创建一个服务器端的SVN服务器之后,会把项目分享到SVN服务器上,这样的话我们团队的所有成员都可以通过SVN来下载一个最新的项目,来完成协作开发。包括我们每天项目代码的一个提交,修改,更新,同时它会对不同成员对同一个项目的修改时产生的冲突进行解决,也可以对当前项目的一些标签进行设定,在某一个时间点找到某一个版本的项目提供了一个非常全面的源代码的版本的功能,使用SVN规范的是,每天都要把最新写的代码提交到SVN服务器上,必须保证是最新的可以运行的代码,每天早上来的时候把最新的代码更新到本地,这样我们可以保证每天的代码可以进行集成,而不至于代码长时间没有进行整合,产生一系列的冲突,影响工作效率,同时,SVN能够 更好地将我们的代码进行管理,如果我们不使用SVN进行管理的话,本地的代码很容易被操作,被删除掉,这样的话,同步在SVN服务器上,就可以减少误删等操作,更好的对每一个时期的版本的代码有个跟踪的过程。
5 介绍一下什么叫做NOSQL?它有什么意义?都有哪些常见的数据库?
【答案】
Nosql是近几年常见的非关系型数据库,这里的nosql指的是NOt-only sql,我们传统的数据库比如mySQL,oracle数据库都是SQL数据库,属于关系型数据库,nosql数据库是非结构化的数据库,就是我们在存储数据表,存储数据的时候,这个结构是可以随时发生变化的,也就是说,我们在创建mysql数据库表的时候,它的数据是固定的,但是在nosql数据库当中,我们在创建一个表的时候,在创建一个记录的时候,它的表结构可以随时发生变化,它是以文本方式存储的,其风格类似于json。这样的话,体现出了它极大的灵活性,比如我们在业务非常的频繁的情况下,有些字段存在有些字段不存在,这样的话,我们可以灵活的选择nosql数据库对非结构化数据进行存储和查询,最常见的nosql数据库有mongodb数据库,mongodb提供了一个全方位的非结构化数据库的管理,我们通过对mongodb数据库的增删改查发现,我们可以对任何一个结构数据对它进行存储,在每一次新增的时候,我们可以扩充表的字段,这个是它提供的很好的一个非结构化的管理功能,同时mongodb也提供了基于数据库和缓存级别的机制,更大的提升了整体的工作效率,总体来说,nosql和SQL数据库的差别在于它存储的文件的类型的时候,nosql更加灵活,更加的去动态扩充表的字段,
提供了很好的过程,它是以文本文件的方式存储。
常见工具与知识扩充2 UML_项目开发流程_敏捷开发_设计模块
1简单介绍一下,什么叫做UML?UML在我们开发中有什么作用?
【答案】
UML是Unified Modeling Language (UML)又称统一建模语言或标准建模语言,我们通过UML更多的是在做系统的分析和设计过程中来使用,UML所常用的一些图形工具用例图,活动图,时序图,构建图,状态图等描述我们的软件系统。用例图就是描述当前系统项目当中,有哪些角色,系统的边界是什么,系统边界内部,系统的功能有哪些,站在用户角度,看系统有哪些功能的。这就叫用例图。第二个叫做时序图,它是描述了我们系统之间各个板块之间数据传递的一个内部流转流程,一般情况下,我们按照系统分层的时候,MVC框架,从前端到controller到service到dao,到缓存在到数据库,这一过程,我们可以用时序图来串相关场景。这是时序图。第三个,活动图,可以理解为流程图,这样的话更多的应用场景就是公司的请假流程就可以通过这个活动图来描述这个业务场景流程。由谁发起的开始,经过了哪些流程环节,最后怎么结束,这整个流程我们可以用活动图来描述。还有一个状态图,也可以理解为状态迁移图,也就是我们在系统当中的模型状态是发生变化的,比如做网站的时候,一些职位状态发生的变化,一开始创建职位的时候,它是初始状态,我们将职位发布之后,它就成了发布状态了,发布完之后,发现职位需要修改,就需要把职位下线,此时职位又变成了下线状态,在进行修改,然后再发布,这个过程就叫做状态的迁移过程,可以通过状态图来描述。除此之外,可能还会用到其他的工具图,去描述一下系统的其他功能。这个时候,我们 通过package包图,类图,描述类关系的图,包括部署,我们的项目最后部署到一个什么样的环境,它的网络环境,它的数据库,这是通过我们的部署图来做的,一般来说,在使用UML的时候,我们只是把它作为一个画图工具而已,不会和我们的Java代码产生一个紧密的对接,这个过程我们也不能把它过重的去设计,更多的是通过这些工具图形去更好的描述我们的软件框架,在分析和设计的时候会使用到UML。
2 简述一下你所开发的项目,它的发开流程是什么样的?
【答案】
这种问题,一定要从项目立项,调研,分析,设计,研发,测试上线这个思路来说。
在项目开发过程中,首先要经过公司项目的立项,公司立项之后,我们会根据项目的目标,来分析项目的功能需求和分析设计,项目的需求分析,我们会把系统的所有的功能点,所有的场景分析完,分析完之后进行系统的设计,设计就是我们基于Java,对整个系统进行分层设计,数据库模块的设计,表结构的设计,类结构的设计,类关系的设计,以及框架层,缓存的设计等,我们能考虑到的宏观的技术体系,都是在设计阶段来完成的。设计完成之后,每个人对自己的模块进行划分,由项目经理带头将所有的模块具体划分到某一个人的工作范围。制定相关计划,每个人有自己的模块,到了开发阶段,开发阶段包括这么几个部分,第一个,编码部分,第二个,单元测试我们每个人写的代码经过单元测试通过之后,再把代码提交到服务器上,每天进行定期提交,经过一个开发周期,项目开发完成之后,我们会把整体的项目进行集成,集成完后打包,部署到我们的测试服务器上,由我们的测试工程师进行整体测试,测试完成之后,如果没有bug,也符合我们当时项目需求分析,达到我们的制定目标的时候,再由我们的测试工程师把项目发布到我们的生产环境中去,这样我们的产品就能为我们的客户在外网上提供服务了。这就是我们项目开发的一个整体的流程。
3 以前你们在项目开发的时候,与没有接触过敏捷开发?谈谈你对敏捷开发的理解。
【答案】
我们在以前的开发中是有过这么一些概念的。我们在项目开发的过程用的就是敏捷开发这么一个管理模式,敏捷开发的要求就是快速迭代,小步快跑。我们所使用的模型叫做scrum,通过敏捷这么一个快速管理办法,我们可以将我们的大项目,比如两年的一个项目把它拆散成两个月一个两个月一个的版本,在第一个版本我们只做核心的特定的一些需求,这样我们在两个月开发完成之后,出现了一些偏差的时候,我们可以船小可以掉头,我们在第二个版本,也就是第二到第四个月的时候,在纳入一些新的版本,完善一下前两个月所碰到的问题,这样两个月一个版本两个月一个版本,两年可以拆分12个版本,这样的话,就可以更好的把控项目的进度,而不至于像传统的开发项目模式,瀑布模式,这种模式一上来就将两年计划定的非常满,两年计划相当于一条线走完,从需求分析,设计,开发,测试上线一条线走完,结束了。这个过程中碰到的所有问题没法回退,那小步快跑,快速迭代这个敏捷开发,两个月一个小版本,更大的减轻了我们的不能回头的这么一个 风险,相应我们快速变化的一个需求,非常给力的这么去做,通过scrum这么一个管理模式。能够使我们在项目开发当中,在项目管理当中更好的应对一些问题,这个就是我们在敏捷开发过程中的应用。
4简要说明一下什么是设计模式?举例说明一下开发当中常见的五种设计模式。
【答案】
软件的设计模式是软件存在多年所形成的反复使用过程中,我们程序员很多年积累起来的通用的技术框架,使用设计模式,是为了代码的可重用性,它的架构,它的代码分层,同时,让我们代码的可靠性,安全性,稳定性更加的健壮,能够使我们的代码被更多人所理解,这就形成了一套设计模式,这个设计模式其实就是这么多年以来,软件行业所形成的一个规范,这个叫做设计模式。那么常见的设计模式有这么几种,1 工厂模式,2 原型模式 3 单例模式 4 适配器模式 5 代理模式 6门面模式 7命令模式等设计模式。
工厂模式:我们一般通过工厂模式来创建我们需要生产的对象。
单例模式:单例模式所管理的对象它在系统当中只有一份实例。
原型模式:也就是多例模式。在系统当中可以存在多份实例。与单例模式相对应。
门面模式;我们系统对外部提供一个接口,这样的话减轻系统与外部的一个耦合度。除此之外,还有代理模式,命令模式。
代理模式:为其他对象提供一个代理以控制对对象的访问。
命令模式:将请求封装成一个对象,从而可用不同的请求对客户参数化,对请求排队或记录请求日志,以及支持可取消的操作。