oracle视图
轉(zhuǎn)自:https://www.cnblogs.com/iamliuxin/p/5617799.html
數(shù)據(jù)庫的真實數(shù)據(jù)都是存在于數(shù)據(jù)表中,數(shù)據(jù)表是反映現(xiàn)實世界的實體關(guān)系。但是,為現(xiàn)實世界的所有關(guān)系創(chuàng)建數(shù)據(jù)表是不現(xiàn)實的。數(shù)據(jù)庫中的視圖解決了這一問題。視圖以物理數(shù)據(jù)未基礎(chǔ),利用更靈活的策略來實現(xiàn)關(guān)系。接下來,我們將從:
視圖介紹、關(guān)系視圖的創(chuàng)建和使用、內(nèi)嵌式圖的使用、對象視圖的使用、物化視圖的使用等幾個方面,
來學(xué)習(xí)視圖的知識,并掌握如何創(chuàng)建和使用各種視圖,同時對各種視圖之間的區(qū)別有清晰的了解。
?
1、視圖簡介:
1.1 什么是視圖
視圖是由已經(jīng)存在的數(shù)據(jù),通過一定的運(yùn)算規(guī)則,來獲得新的數(shù)據(jù)集合。這使得用戶可以更加靈活的自定義數(shù)據(jù)集合,視圖同時為數(shù)據(jù)安全性提供了一種控制策略。
(1) 視圖的產(chǎn)生
之前一篇博文中講到了數(shù)據(jù)表的創(chuàng)建規(guī)則,由于遵循第三范式,表在設(shè)計時,應(yīng)當(dāng)避免數(shù)據(jù)冗余,而另一方面,使用各種組合數(shù)據(jù)更加常用,設(shè)計規(guī)則卻禁止為組合數(shù)據(jù)創(chuàng)建新的數(shù)據(jù)表。
比如:表employees存儲了員工的基本信息,其中包括了員工ID、員工姓名、職位、年齡、地址。表salary存儲了員工工資信息,其中包括了工資ID、員工ID、月份、工資、貨幣種類。
現(xiàn)在需要為財務(wù)人員準(zhǔn)備一個新的數(shù)據(jù)集合,該數(shù)據(jù)集合存儲了員工ID、員工姓名、員工年齡、月份及當(dāng)月工資。很明顯,創(chuàng)建新表employee_salary,以滿足財務(wù)人員的需求是不可取的,此時,創(chuàng)建視圖來解決該問題是最佳途徑。
下圖演示了針對表employees每行數(shù)據(jù),根據(jù)employee_id列值相等的條件,在表salary中篩選記錄,并最終組成新的數(shù)據(jù)集合。這種關(guān)系運(yùn)算的存儲在視圖vw_employees終。對于用戶來說,只需要定義運(yùn)算規(guī)則,而運(yùn)算貴的載體-----視圖,并不存儲真實的數(shù)據(jù)。
(2)視圖的本質(zhì)
從關(guān)系代數(shù)理論上來說,數(shù)據(jù)表可以看做關(guān)系。這種關(guān)系往往代表了現(xiàn)實世界的真實實體。而關(guān)系可以通過各種運(yùn)算(交、差、并、投影)來獲得新的關(guān)系。
在查詢員工工資狀況的實例中,可以通過表之間的關(guān)系運(yùn)算獲得財務(wù)人員所需的結(jié)果集合。該結(jié)果集具有臨時性,一旦使用完畢,即可丟棄。這些結(jié)果數(shù)據(jù),并不形成真正的數(shù)據(jù)表,也不會持久化到數(shù)據(jù)庫中。視圖也不存儲查詢的結(jié)果,但是存儲了查詢的定義。也就是說,對于關(guān)系運(yùn)算的運(yùn)算步驟進(jìn)行存儲。因此,視圖的本質(zhì)就是關(guān)系運(yùn)算的定義。
?
1.2 為啥使用視圖咧
視圖是絕大部分?jǐn)?shù)據(jù)庫開發(fā)中都會使用的概念。使用視圖大致有兩個方面的原因。
(1)封裝查詢
數(shù)據(jù)庫雖然可以存儲海量數(shù)據(jù),但是在數(shù)據(jù)表設(shè)計上卻不可能為每種關(guān)系創(chuàng)建數(shù)據(jù)表。例如:對于學(xué)生表,存儲了學(xué)生信息,學(xué)生的屬性包括學(xué)號、姓名、年齡、地址等信息;而學(xué)生成績表只存儲了學(xué)生學(xué)號、科目、成績等信息,現(xiàn)需要獲得學(xué)生姓名及成績信息,那么久需要創(chuàng)建一個關(guān)系,該關(guān)系需要包含學(xué)生姓名、科目、成績。但為該關(guān)系創(chuàng)建一個新的數(shù)據(jù)表,并利用實際信息進(jìn)行填充,以備查詢使用,是不合適的。因為這種做法很明顯的造成了數(shù)據(jù)庫中數(shù)據(jù)的大量冗余。
視圖則是解決該問題的最佳策略,因為視圖可以存儲查詢定義(或者關(guān)系運(yùn)算),那么,一旦使用視圖存儲了查詢定義,就如同存儲了一個新的關(guān)系。用戶可以直接對視圖中所存儲的關(guān)系進(jìn)行各種操作,就如同面對的是真實的數(shù)據(jù)表。
?
(2)靈活的控制安全性
一個數(shù)據(jù)表可能含有很多列,但是這些列的信息,對于不同角色的用戶,可訪問的權(quán)限有可能不同。例如:在員工表中,可能存在著員工工號、姓名、年齡、職位、地址、社會關(guān)系等信息。對于普通用戶,有可能需要訪問員工表,來查看某個工號的員工的姓名、職位等信息,而不允許查看家庭地址、社會關(guān)系等信息;對于高級用戶,則需要關(guān)注所有信息,那么,久涉及到數(shù)據(jù)表的安全性。
利用視圖可以靈活的實現(xiàn)這一策略,例如:可以首先創(chuàng)建名為vw_employees的視圖,該視圖的查詢定義為,選擇員工表中員工工號、姓名、職位等3列,這相當(dāng)于在員工關(guān)系中,進(jìn)行投影運(yùn)算,即選擇員工工號、姓名、職位等3個屬性,形成新的關(guān)系。
同樣的,對于高級用戶,可以創(chuàng)建名為vw_employees_hr的視圖,該視圖選擇員工表中所有列。
然后,對于兩種角色分別分配兩個視圖的查詢權(quán)限,與實際的數(shù)據(jù)表employees隔離開來,從而控制數(shù)據(jù)訪問的安全性。
?
2、創(chuàng)建和使用關(guān)系視圖
oracle中的視圖,按照創(chuàng)建和使用方式的不同,可以分為四類:關(guān)系視圖、內(nèi)嵌視圖、對象視圖和物化視圖。
關(guān)系視圖是4種視圖中最簡單,同時也最常用的視圖。關(guān)系視圖可以看做對簡單或復(fù)雜查詢的定義。他的輸出可以看做一個虛擬的表。
2.1 創(chuàng)建關(guān)系視圖
oracle視圖是作為數(shù)據(jù)庫對象存在的。因此,創(chuàng)建之后也可以通過工具或數(shù)據(jù)字典來查看視圖的相關(guān)信息,接下來,要講解的是:關(guān)系視圖的創(chuàng)建和如何查看視圖的屬性信息。
(1)創(chuàng)建關(guān)系視圖
創(chuàng)建關(guān)系視圖應(yīng)該使用create view命令,其語法形式如下所示:
create view 視圖名稱 as 查詢語句|關(guān)系運(yùn)算
其中,create view是創(chuàng)建關(guān)系視圖的命令,其后緊跟視圖名稱;as 后面連接的是視圖的查詢定義(或者說關(guān)系運(yùn)算)。
例子:在數(shù)據(jù)庫中存在著名為employees的數(shù)據(jù)表,如需創(chuàng)建針對普通用戶的視圖vw_employees。該視圖僅可以訪問表中的員工ID、員工姓名,以及員工職位,那么可以利用如下的SQL語句。
create view vw_employees as select employee_id, employee_name, employee_position from employees;
其中,create view 向數(shù)據(jù)庫發(fā)送創(chuàng)建視圖命令,as 關(guān)鍵字連接創(chuàng)建命令與視圖定義;select employee_id、employee_name和employee_position from t_employees用于獲取表t_employees中的employee_id、employee_name和employee_position 3 列。
(2)查看視圖定義
視圖一旦創(chuàng)建,其定義即可存在于數(shù)據(jù)庫中,可以通過PL/SQL Developer的veiws 窗口查看視圖VW_EMPLOYEES在數(shù)據(jù)庫中的信息。
如果是有數(shù)據(jù)字典,也可以在輸入SQL語句進(jìn)行查詢,比如:
select view_name, text from user_views where view_name= 'VW_EMPLOYEES';
view ? ? ? ? ? ? ? ? ? ? ? ? ?text
vw_employee ? ? ? ? select employee_id, employee_name, employee_position from employees
其中,view_name列為視圖名稱,text列為視圖定義。
?
2.2 使用關(guān)系視圖
視圖一旦創(chuàng)建,用戶可以像查詢數(shù)據(jù)表一樣查詢視圖中的數(shù)據(jù),但是,對于插入和更新操作來說,情況則有些不同。
(1)查詢視圖
例子:在創(chuàng)建了視圖VW_EMPLOYEES之后,即可利用查詢語句來獲得視圖中所包含的數(shù)據(jù),如下:
SQL>select * from vw_employeess;
(2)更新視圖數(shù)據(jù)
用戶可以利用update語句更新視圖中的數(shù)據(jù),而視圖本身并不存儲數(shù)據(jù),其數(shù)據(jù)來源于基礎(chǔ)數(shù)據(jù)表,因此,更新視圖數(shù)據(jù),實際是更新基礎(chǔ)表中的數(shù)據(jù)。
例子:在員工視圖vw_employees中,現(xiàn)在需要將員工“劉俊”職位調(diào)整為“高級工程師”,那么可以直接更新視圖,響應(yīng)的SQL語句:
SQL>update vw_employees set employee_position = '高級工程師' where employee_name='劉俊';
其中,update為更新命令;vw_employees為update 命令的操作對象;set employee_position = '高級工程師',employee_name='劉俊',是指定更新條件。
但是,此時更新的實際是將表employees中的數(shù)據(jù)進(jìn)行了修改。
綜合視圖操作及查詢結(jié)果可知,對視圖的更新操作,實際為更新基礎(chǔ)表中的數(shù)據(jù),由于視圖僅存儲查詢定義,因此,一旦基礎(chǔ)表中的數(shù)據(jù)被修改,則修改后的結(jié)果可以立即反映到視圖中。
2.3 向視圖插入數(shù)據(jù)
同樣,可以利用insert語句,向視圖中插入數(shù)據(jù)。
例子:在視圖vw_employees中,插入新員工“張三”的相關(guān)信息,其SQL語句如下所示。
SQL>insert into vw_employees values (6 , '張三', '測試工程師')
由于,該視圖只能查到該3項內(nèi)容,所以,在向視圖vw_employees中插入數(shù)據(jù)時,無法為列employee_age和列employee_address指定數(shù)據(jù),因此,在基礎(chǔ)表employees中,對應(yīng)記錄的employee_age列和employee_address列的值為空。
2.4 總結(jié)利用關(guān)系視圖修改數(shù)據(jù)。
利用關(guān)系視圖,除了插入數(shù)據(jù)和更新數(shù)據(jù)之外,還可以刪除其中的數(shù)據(jù)。表面上看起來,可以通過視圖對基礎(chǔ)表進(jìn)行任何修改,但事實并非如此,與之相反,大多數(shù)時候,并不能直接利用視圖修改基礎(chǔ)表數(shù)據(jù)。
例子:oracle內(nèi)置視圖user_update_columns定義了用戶視圖中各列的可更新情況,可以通過如下SQL語句進(jìn)行查看。
SQL>select table_name, column_name, updatable, insertable, deletable?
from user_updatable_columns
where table_name = 'VW_EMPLOYEES'
其中,TABLE_NAME列為表名(在此,為視圖名,這里也印證了oracle往往將視圖當(dāng)做普通數(shù)據(jù)表處理);COLUMN_NAME列為視圖中的列名;UPDATBALE、INSERTABLE和DELETABLE分別代表列的可更新、可插入以及可刪除的情況。
對于更新操作,只要該列可更新,那么饑渴利用視圖進(jìn)行更新;而對于插入和刪除操作,則必須所有列均可執(zhí)行插入和刪除操作,才能利用視圖進(jìn)行操作。
?
2.3 修改/刪除視圖
在創(chuàng)建了關(guān)系視圖vw_employees之后,可以對其進(jìn)行修改和刪除操作。
(1)修改視圖
修改視圖的過程即為重新定義視圖的過程。可以通過首先刪除視圖,然后再次創(chuàng)建實現(xiàn)。另外,oracle也提供了一個專門的命令----create or replace view 來重新定義視圖。其語法形式如下所示:
create or replace view 視圖名稱 ?as ?查詢語句 | 關(guān)系運(yùn)算
例子:假設(shè)現(xiàn)在需要為視圖vw_employees添加新列employee_age,那么可以利用如下SQL語句。
create or repalce view vw_employees as
select employee_id, employee_name, employee_position, employee_age from employees
其中,create or replace view vw_employees用于創(chuàng)建或者替換視圖vw_employees的定義;as 之后的查詢語句為視圖的新定義,在新定義中增加了列employee_age。
【注意】create or replace view命令的作用,當(dāng)同名視圖不存在時,將執(zhí)行創(chuàng)建命令;否則將執(zhí)行替換命令。
(2)刪除視圖
刪除視圖的動作實際為刪除數(shù)據(jù)庫中的對象操作,因此該操作為DML操作,如同刪除數(shù)據(jù)表對象,刪除視圖也應(yīng)該使用drop命令,其語法形式如下所示。
drop view view_name
其中,drop view向數(shù)據(jù)庫發(fā)送刪除視圖命令;view_name則指定了要刪除的視圖名稱。
例子:如需刪除視圖vw_employees,則可以利用如下SQL語句。
drop view vw_employees;
?
2.4 只讀視圖
上面講述了修改視圖數(shù)據(jù),有時,并不希望用戶通過視圖修改數(shù)據(jù),則可以創(chuàng)建只讀視圖,創(chuàng)建只讀視圖應(yīng)該使用read only選項,其基本語法形式如下所示。
create or replace view 視圖名稱 as查詢語句
with read only
其中,with read only 選項表示該視圖將被創(chuàng)建為只讀視圖。
?
2.5 聯(lián)接視圖
對于視圖定義來說,其數(shù)據(jù)可以來源于一個數(shù)據(jù)表,也可以來源多個數(shù)據(jù)表或者其他視圖的聯(lián)接。事實上,聯(lián)接視圖在實際開發(fā)中更加常用,本節(jié)將講述聯(lián)接視圖的使用。
例子:可以利用create or replace view定義一個聯(lián)接視圖,只是視圖定義更加復(fù)雜而已,在表employees與表salary中分別定義了員工與工資信息,則可以利用create or replace view創(chuàng)建視圖。
create or replace view vw_employee_salary as
select e.employee_id, e.employee_name, s.month, s.salary
from employees e, salary s
where e.employee_id = s.employee_id
其中as關(guān)鍵字之后使用了表employees與表salary的聯(lián)接獲得新的數(shù)據(jù)集合。聯(lián)接條件為表employees中的employee_id與表salary中的employee_id相等。在視圖創(chuàng)建成功之后,即可查詢表中的數(shù)據(jù)。
?
2.6 強(qiáng)制創(chuàng)建視圖
歸根結(jié)底,視圖數(shù)據(jù)的來源是基礎(chǔ)數(shù)據(jù)表。有時,視圖的基礎(chǔ)表尚未創(chuàng)建,但是仍然希望創(chuàng)建基于不存在的數(shù)據(jù)表的視圖。
例子:開發(fā)者預(yù)期有名為customer的數(shù)據(jù)表,該表至少包含以下列。
現(xiàn)需要創(chuàng)建一個名為vw_customer的視圖,該視圖僅包含以下列customer_id、customer_code、customer_name、customer_level和contact_telephone。但是,視圖創(chuàng)建者無權(quán)創(chuàng)建實際的數(shù)據(jù)表。但是又不能等待表的預(yù)期創(chuàng)建者的工作,此時,可以使用force選項來強(qiáng)制創(chuàng)建視圖。利用force選項,強(qiáng)制創(chuàng)建視圖的語法如下所示。
create or replace force view 視圖名稱 as 查詢語句 | 關(guān)系運(yùn)算
在PL/SQL Developer中強(qiáng)制創(chuàng)建視圖vw_customer。
SQL>create or replace force view vw_customer as
select customer_id, customer_code, customer_name, contact_telephone
from customer;
轉(zhuǎn)載于:https://www.cnblogs.com/sharpest/p/10508371.html
總結(jié)
- 上一篇: 谷歌zxing 二维码生成工具
- 下一篇: 通过图片优化,我将网站大小减少了62%