背景原因:
一方面,在一个项目的实际开发过程中牵涉到复杂业务的时候,我们不可避免的需要使用中间表来进行数据连接。
一方面,采用Hibernate进行主外键进行关联:多对多,多对一,一对一等,采用主外键关联在数据的操作过程中具有很强的耦合性,尤其对于需要经常删改数据表而言,不建议采用主外键关联这种模式。
另一方面,如果我们采用中间表(多个对象关联)的话,当数据过大在性能上又面临严峻考验。
所以,sql视图的出现,在解决中间表的业务逻辑上是不错的选择。
什么是视图?
视图是一张虚拟表,视图只供查询,数据不可更改,查询数据来源于我们建立的实体表
视图是已经编译好的sql语句
视图(view)是在基本表之上建立的表
常用场景:视图适合于多表连接浏览时使用。不适合增、删、改。
使用视图的优势?
视图可以将多个复杂关联表,提取出我们需要的信息,优化查询速度。
1.简化操作
将常用的聚合函数或多表查询这些查询语句放到视图中,简化了操作,每次只要select * from view就可以了。
2.安全性
只让用户查看部分数据,同时,用户无法对视图进行随意的修改和删除,增加了安全性。
3.逻辑数据独立性。
视图可以使应用程序和数据库表在一定程度上独立。如果没有视图,应用一定是建立在表上的。有了视图之后,程序可以建立在视图之上,从而程序与数据库表被视图分割开来
视图的作用
(1)当一个查询你需要频频的作为子查询使用时,视图可以简化代码,直接调用而不是每次都去重复写这个东西,有点高级语言中的封装的意思吧。
(2)其他的用处:比如说你是一个系统的数据库管理员,你需要给他人提供一张表的某两列数据,而不希望他可以看到其他任何数据,这样你就可以给他建一个只有这两列数据的视图,然后把视图公布给他。
应该案例
我们先建立三张表;如下:
这个是典型的一对多,多对一和一对一的关系,那么,假如每张表的数据都在一万条数据以上,现在查询角色为ROLE_EPES_ADMIN的所有员工名称?
首先,我们分析一下,角色为ROLE_EPES_ADMIN?首先是在role表name=ROLE_EPES_ADMIN,那么我们会有一条Sql :where name_='ROLE_EPES_ADMIN'
select * from [dbo].[SYS_Role] where name_='ROLE_EPES_ADMIN'
查询出得到role_id,然后再到userRole表中根据role_id查询userId list,
select * from [dbo].[SYS_UserRole] where role_id_='298703625fc8bfc3015fc8ca80560009'
在使用这些userId 循环使用sql查询: from [dbo].[SYS_User] where id_=userId 循环得到user?
select * from [dbo].[SYS_User] where id_='01356680'
select * from [dbo].[SYS_User] where id_='01526217'
select * from [dbo].[SYS_User] where id_='01171278'
select * from [dbo].[SYS_User] where id_='SN00001'
select * from [dbo].[SYS_User] where id_='01169014'
是不是很累赘?查询是不是很影响性能?
观察得知,这三张表是通过[SYS_UserRole]中间表进行关联的,如果我们将三张表组成一张表,是不是很方便?
select a.login_id_,a.user_name_,a.country_,b.role_id_,c.name_,c.description_
from [dbo].[SYS_User] a
inner join [dbo].[SYS_UserRole] b
on a.id_=b.user_id_
left join [dbo].[SYS_Role] c
on b.role_id_=c.id_
以上仅罗列需要的字段,没意义的字段也不展示在view表中(封装,安全性,针对性),看一下结果:
那么我们想查询角色为ROLE_EPES_ADMIN的员工姓名,where c.name_='ROLE_EPES_ADMIN'',获取的list循环得到Object,通过Object.getUserName,就可以了
所以需要将查询到的结果,建立为一张虚拟表,这样才能操作,通过这个: create view 视图名 as 命令 建立:
create view [dbo].[uvw_SYS_UserRole] as
(select a.login_id_,a.user_name_,a.country_,b.role_id_,c.name_,c.description_
from [dbo].[SYS_User] a
inner join [dbo].[SYS_UserRole] b
on a.id_=b.user_id_
left join [dbo].[SYS_Role] c
on b.role_id_=c.id_)
意思就是将查询结果创建为名称为uvw_SYS_UserRole的一张虚拟表:
我们在使用视图的时候,需要把它看做为一张表,建立一张实体表需要做的步骤,视图也都需要(实例化,配置映射文件,对象的属性get,set方法)
则我们想查询角色为ROLE_EPES_ADMIN的员工姓名,执行一下SQL,并遍历即可
select * from uvw_SYS_UserRole where name_='ROLE_EPES_ADMIN'
注意视图所查询出来的数据只能进行查看,不能增删改!
例子数据库为SQL Server,工具SQL Server Management Studio