oracle--07檢視

zhyp29發表於2016-05-24
Oracle——07檢視
oracle:檢視操作,view
檢視實際上是一個或多個表的預定義查詢,這些表成為基表。
檢視中並不儲存資料,他是會訪問基表中的行.

建立檢視
CREATE [ OR REPLACE ] VIEW [{FORCE |NOFORCE}] view_name
[(alias_name [,alias_name…])] AS subsquery
[WITH {CHECK OPTION |READ ONLY} CONSTRAINT constraint_name];
 

NOFORCE 如果基表不存在則不建立檢視,預設為NOFORCE
alias_name 為子查詢中的表示式指定別名。

subquery 子查詢
WITH CHECK OPTION 說明只有子查詢檢索的行才能被插入、修改或刪除。預設情況下,在出入、更新或修改行之前並不會檢查這些行是否能被子查詢檢索。

constraint_name 指定 WITH CHECK OPTION 或 READ ONLY 約束的名稱
WITH READ ONLY  只能對基表中的行進行只讀訪問。

檢視分兩種:
簡單檢視:包含一個子查詢,他只是從一個基表中檢索資料。

發雜檢視:包含一個子查詢,特點:
從多個基表中間索資料
使用GROUP BY 或 DISTINCT 子句對行進行分組
包含函式呼叫
只能對簡單檢視進行DML;

具有CHECK OPTION 約束的檢視
CREATE VIEW view_name AS
SELECT *
FROM table_name
where id<15
WITH CHECK OPTION CONSTRAINT constraint_name;
 

這樣對檢視插入 id >=15 的資料將會出錯。
獲得有關檢視定義的資訊
DESC[RIBE] view_name;
SELECT *
FROM user_views
WHERE view_name ='xx';
 

下面那個可以獲得檢視的權證 subquery 語句

獲得有關檢視約束的資訊
SELECT *
FROM user_constraints
WHERE table_name = 'xxxx';
 

修改檢視
通常直接 CREATE OR REPLACE 建立一個新的檢視

刪除檢視的約束
ALTER VIEW view_name
DROP CONSTRAINT constraint_name;
 

刪除檢視
DROP VIEW view_name;
 

 
1.1 概念
       檢視-----是由SELECT查詢語句(可以是單表或者多表查詢)定義的一個"邏輯表",只有定義而無資料,是一個"虛表". 在建立檢視時,只是將檢視的定義資訊儲存在資料字典中, 而並不將實際的資料複製到任何地方, 即不需要在表空間中為檢視分配儲存空間. 檢視是檢視和操縱基表資料的一種方法, 可以像使用表一樣使用檢視.

        tips: 查詢檢視沒有什麼限制, 插入/更新/刪除檢視的操作會受到一定的限制; 所有針對檢視的操作都會影響到檢視的基表; 為了防止使用者通過檢視間接修改基表的資料, 可以將檢視建立為只讀檢視(帶上with read only選項). 

檢視中的資料會隨基表的更新而自動更新.
檢視猶如基表的一個"視窗", 通過這個"視窗", 可以實施許多管理. 在一個檢視中可以定義的最大列數為1000, 與表的限制相同

檢視約束: 允許在檢視上生成約束, 如"主鍵約束、唯一鍵約束、外來鍵約束、檢查約束"等. 但檢視上的約束不是強制性的, 而是宣告性的. 檢視約束的語法與表相同. 在建立檢視時, 可以使用with check option選項,給檢視定義check約束,使其只能查詢、操作滿足check約束的記錄行.

1.2  作用
        1)提供各種資料表現形式, 可以使用各種不同的方式將基表的資料展現在使用者面前, 以便符合使用者的使用習慣(主要手段: 使用別名).

        2)隱藏資料的邏輯複雜性並簡化查詢語句, 多表查詢語句一般是比較複雜的, 而且使用者需要了解表之間的關係, 否則容易寫錯; 如果基於這樣的查詢語句建立一個檢視, 使用者就可以直接對這個檢視進行"簡單查詢"而獲得結果. 這樣就隱藏了資料的複雜性並簡化了查詢語句. 這也是oracle提供各種"資料字典檢視"的原因之一,all_constraints就是一個含有2個子查詢並連線了9個表的檢視(在catalog.sql中定義).

        3)執行某些必須使用檢視的查詢. 某些查詢必須藉助檢視的幫助才能完成. 比如, 有些查詢需要連線一個分組統計後的表和另一表, 這時就可以先基於分組統計的結果建立一個檢視, 然後在查詢中連線這個檢視和另一個表就可以了.

        4)提供某些安全性保證. 檢視提供了一種可以控制的方式, 即可以讓不同的使用者看見不同的列, 而不允許訪問那些敏感的列, 這樣就可以保證敏感資料不被使用者看見.

        5)簡化使用者許可權的管理. 可以將檢視的許可權授予使用者, 而不必將基表中某些列的許可權授予使用者, 這樣就簡化了使用者許可權的定義.

1.3  建立檢視
        許可權: 要在當前方案中建立檢視, 使用者必須具有create view系統許可權; 要在其他方案中建立檢視, 使用者必須具有create any view系統許可權. 檢視的功能取決於檢視擁有者的許可權.

        語法: create [ or replace ] [ force ] view [schema.]view_name
                      [ (column1,column2,...) ]
                      as 
                      select ...
                      [ with check option ] [ constraint constraint_name ]
                      [ with read only ];
        tips:
        or replace: 如果存在同名的檢視, 則使用新檢視"替代"已有的檢視

        force: "強制"建立檢視,不考慮基表是否存在,也不考慮是否具有使用基表的許可權

        column1,column2,...:檢視的列名, 列名的個數必須與select查詢中列的個數相同; 如果select查詢包含函式或表示式, 則必須為其定義列名.  此時, 既可以用column1, column2指定列名, 也可以在select查詢中指定列名.

        with check option: 指定對檢視執行的dml操作必須滿足“檢視子查詢”的條件即,對通過檢視進行的增刪改操作進行"檢查",要求增刪改操作的資料, 必須是select查詢所能查詢到的資料,  否則不允許操作並返回錯誤提示. 預設情況下, 在增刪改之前"並不會檢查"這些行是否能被select查詢檢索到. 

        with read only:建立的檢視只能用於查詢資料, 而不能用於更改資料.

1.3.1 建立簡單檢視
        是指基於單個表建立的,不包含任何函式、表示式和分組資料的檢視。
         示例1:基於emp表建立一個vw_emp檢視
         create view vw_emp
         as
         select  empno,ename,job,hiredate,deptno from emp; --------建立簡單檢視
   
 desc vw_emp; --------象表一樣使用

select * from vw_emp  where  deptno=10;--------查詢
         insert into vw_emp values(1234,'JACK','CLERK','29-4月-1963',10);--------增加
         update vw_emp set ename='劉德華' where ename='JACK';--------更新
         delete vw_emp where ename='劉德華'; --------刪除
         
         create view vw_emp_readonly
         as
         select  empno,ename,job,hiredate,deptno from emp
         with read only ; --------建立只讀檢視,只能用於執行select語句
         delete from vw_emp_readonly where empno=1234;--------刪除失敗
         create view vw_emp_check
         as
         select  empno,ename,job,hiredate,deptno 
         from emp where deptno=10
         with check option constraint vw_emp_chk ;
         --------建立檢查檢視:對通過檢視進行的增刪改操作進行檢查,
                                       要求增刪改操作的資料必須是select查詢所能查詢到的資料。           
         insert into vw_emp_check
         values(1235,'JACK','CLERK','29-4月-1963',20);
         --------20號部門不在查詢範圍內,違反檢查約束
         delete from vw_emp_check  where empno=1234;
         --------所刪除的資料在查詢範圍內,不違反檢查約束
1.3.2 建立連線檢視
        是指基於多個表所建立的檢視,即,定義檢視的查詢是一個連線查詢。 主要目的是為了簡化連線查詢
        示例1: 查詢部門編號為10和30的部門及僱員資訊
              create view vw_dept_emp
              as
              select a.deptno,a.dname,a.loc,b.empno,b.ename,b.sal
              from dept a , emp b
              where a.deptno=b.deptno 
              and  a.deptno in (10,30);
              select * from vw_dept_emp;
  
1.3.3 建立複雜檢視
        是指包含函式、表示式、或分組資料的檢視。主要目的是為了簡化查詢。 主要用於執行查詢操作,並不用於執行DML操作。
         注意:當檢視的select查詢中包含函式或表示式時,必須為其定義列別名。
         示例1:查詢目前每個崗位的平均工資、工資總和、最高工資和最低工資。
              create view vw_emp_job_sal
              (job,avgsal,sumsal,maxsal,minsal)
              as
              select job,avg(sal),sum(sal),max(sal),min(sal)
              from emp
              group by job;
              select * from vw_emp_job_sal;
1.3.4 強制建立檢視
        正常情況下,如果基表不存在,建立檢視就會失敗。但是可以使用force選項強制建立檢視(前提:建立檢視的語句沒有語法錯誤!),此時該檢視處於失效狀態。
        示例1:
              create force view  vw_test_tab
              as
              select c1,c2 from test_tab;--------會出現“警告: 建立的檢視帶有編譯錯誤。”
              select object_name,status from  user_objects
              where  object_name='VW_TEST_TAB';--------檢視狀態:INVALID
              select  *  from vw_test_tab;--------報錯
              create table test_tab--------先建表
              (c1 number(9) primary key, c2  varchar2(20),c3 varchar2(30));
              select  *  from vw_test_tab;--------自動編譯失效的檢視
              select object_name,status from  user_objects
              where  object_name='VW_TEST_TAB';--------檢視狀態:VALID               
1.4 更改檢視
          在對檢視進行更改(或重定義)之前,需要考慮如下幾個問題:
          之一——由於檢視只是一個虛表,其中沒有資料,所以更改檢視只是改變資料字典中對該檢視的
                       定義資訊,檢視的所有基礎物件都不會受到任何影響
          之二——更改檢視之後,依賴於該檢視的所有檢視和PL/SQL程式都將變為INVALID(失效)狀態
          之三——如果以前的檢視中具有with check option選項,但是重定義時沒有使用該選項,
                       則以前的此選項將自動刪除

1.4.1 更改檢視的定義
          方法——執行create or replace view語句。這種方法代替了先刪除(“許可權也將隨之刪除”)
                       後建立的方法,會保留檢視上的許可權,但與該檢視相關的儲存過程和檢視會失效。
          示例1:create or replace view v_test_tab
                      as
                      select c1,c2||' + '||c3  c23 from test_tab;
   
1.4.2 檢視的重新編譯
           語法:alter view 檢視名 compile;
           作用:當檢視依賴的基表改變後,檢視會“失效”。為了確保這種改變“不影響”檢視和依賴於該檢視的
                     其他物件,應該使用 alter view 語句“明確的重新編譯”該檢視,從而在執行檢視前發現重新
                     編譯的錯誤。檢視被重新編譯後,若發現錯誤,則依賴該檢視的物件也會失效;若沒有錯誤,
                     檢視會變為“有效”。
           許可權:為了重新編譯其他模式中的檢視,必須擁有alter any table系統許可權。
           注意:當訪問基表改變後的檢視時,oracle會“自動重新編譯”這些檢視。
           示例1:select last_ddl_time,object_name,status
                       from  user_objects
                       where  object_name='V_TEST_TAB';——檢視的狀態:有效
                       alter table test_tab  modify (c2  varchar2(30));——修改c2列的長度
                       select last_ddl_time,object_name,status
                       from  user_objects
                       where  object_name='V_TEST_TAB';——檢視的狀態:失效
                       alter view v_test_tab compile;——明確的重新編譯
                       select last_ddl_time,object_name,status
                       from    user_objects
                       where  object_name='V_TEST_TAB';——檢視的狀態:有效
            思考:若上述程式碼修改的不是列長,而是表名,結果又會如何?
                      <警告:更改的檢視帶有編譯錯誤;檢視狀態:失效>
                                           
1.5 刪除檢視
        可以刪除當前模式中的任何檢視;
        如果要刪除其他模式中的檢視,必須擁有DROP ANY VIEW系統許可權;
        檢視被刪除後,該檢視的定義會從詞典中被刪除,並且在該檢視上授予的“許可權”也將被刪除。
        檢視被刪除後,其他引用該檢視的檢視及儲存過程等都會失效。
       示例1:drop view vw_test_tab;
1.6 檢視檢視
        使用資料字典檢視
         dba_views——DBA檢視描述資料庫中的所有檢視
         all_views——ALL檢視描述使用者“可訪問的”檢視
         user_views——USER檢視描述“使用者擁有的”檢視
         dba_tab_columns——DBA檢視描述資料庫中的所有檢視的列(或表的列)
         all_tab_columns——ALL檢視描述使用者“可訪問的”檢視的列(或表的列)
         user_tab_columns——USER檢視描述“使用者擁有的”檢視的列(或表的列)
         示例1:查詢當前方案中所有檢視的資訊
         desc user_views;
         set long 400;
         select view_name,text  from user_views;
         示例1:查詢當前方案中指定檢視(或表)的列名資訊
         select * from user_tab_columns where table_name='VW_DEPT';
1.7 在連線檢視上執行DML操作
         在檢視上進行的所有DML操作,最終都會在基表上完成;
         select 檢視沒有什麼限制,但insert/delete/update有一些限制
1.7.1 在檢視上執行DML操作的步驟和原理
         第一步:將針對檢視的SQL語句與檢視的定義語句(儲存在資料字典中)“合併”成一條SQL語句
         第二步:在記憶體結構的共享SQL區中“解析”(並優化)合併後的SQL語句
         第三步:“執行”SQL語句
                      示例:
                      假設檢視v_emp的定義語句如下:
                      create view v_emp 
                      as
                      select empno,ename,loc
                      from employees emp,departments dept
                      where emp.deptno=dept.deptno and dept.deptno=10;
                      當使用者執行如下查詢語句時:
                      select ename  from  v_emp
                      where empno=9876;
                      oracle將把這條SQL語句與檢視定義語句“合併”成如下查詢語句:
                      select  ename  
                      from employees emp,departments dept
                      where emp.deptno=dept.deptno  and dept.deptno=10
                      and empno=9876;
        然後,解析(並優化)合併後的查詢語句,並執行查詢語句
1.7.2 查詢檢視“可更新”(包括“增刪改”)的列
        使用資料字典檢視
        dba_updatable_columns——顯示資料庫所有檢視中的所有列的可更新狀態
        all_updatable_columns——顯示使用者可訪問的檢視中的所有列的可更新狀態                                    
        user_updatable_columns——顯示使用者擁有的檢視中的所有列的可更新狀態
        示例1: 查詢v_stu_dept中的哪些列是可更新的
              select table_name,column_name,insertable,updatable,deletable
              from    user_updatable_columns
              where table_name='V_STU_DEPT';
1.7.3 可更新連線檢視
       如果建立連線檢視的select查詢“不包含”如下結構,
       並且遵守連線檢視的“更新準則”,
       則這樣的連線檢視是“可更新”的:
       之一:集合運算子(union,intersect,minus)
       之二:DISTINCT關鍵字
       之三:GROUP BY,ORDER BY,CONNECT BY或START WITH子句
       之四:子查詢
       之五:分組函式
       之六:需要更新的列不是由“列表示式”定義的
       之七:基表中所有NOT NULL列均屬於該檢視
1.7.4 鍵值儲存表
        如果連線檢視中的一個“基表的鍵”(主鍵、唯一鍵)在它的檢視中仍然存在,
        並且“基表的鍵”仍然是“連線檢視中的鍵”(主鍵、唯一鍵);
        即,某列在基表中是主鍵|唯一鍵,在檢視中仍然是主鍵|唯一鍵
        則稱這個基表為“鍵值儲存表”。
              
         一般地,由主外來鍵關係的2個表組成的連線檢視,外來鍵表就是鍵值儲存表,而主鍵表不是。 
1.7.5 連線檢視的更新準則
        之一:一般準則——(講)
                        任何DML操作,只能對檢視中的鍵值儲存表進行更新,
                        即,“不能通過連線檢視修改多個基表”;
                        在DML操作中,“只能使用連線檢視定義過的列”;
                        “自連線檢視”的所有列都是可更新(增刪改)的
        之二:insert準則
                       在insert語句中不能使用“非鍵值儲存表”中的列(包括“連線列”);
                       執行insert操作的檢視,至少應該“包含”鍵值儲存表中所有設定了約束的列;
                       如果在定義連線檢視時使用了WITH CHECK OPTION 選項,
                       則“不能”針對連線檢視執行insert操作                                     
       之三:update準則
                        鍵值儲存表中的列是可以更新的;
                        如果在定義連線檢視時使用了WITH CHECK OPTION 選項,
                        則連線檢視中的連線列(一般就是“共有列”)和基表中的“其他共有列”是“不可”更新的,
                        連線列和共有列之外的其他列是“可以”更新的
      之四:delete準則
                        如果在定義連線檢視時使用了WITH CHECK OPTION 選項,
                        依然“可以”針對連線檢視執行delete操作

ORACLE 建立與使用檢視

一.what(什麼是檢視?)

1.檢視是一種資料庫物件,是從一個或者多個資料表或檢視中匯出的虛表,檢視所對應的資料並不真正地儲存在檢視中,而是儲存在所引用的資料表中,檢視的結構和資料是對資料表進行查詢的結果。
2.根據建立檢視時給定的條件,檢視可以是一個資料表的一部分,也可以是多個基表的聯合,它儲存了要執行檢索的查詢語句的定義,以便在引用該檢視時使用。
 

二.why(為什麼要用檢視?檢視的優點)

1.簡化資料操作:檢視可以簡化使用者處理資料的方式。
2.著重於特定資料:不必要的資料或敏感資料可以不出現在檢視中。
3.檢視提供了一個簡單而有效的安全機制,可以定製不同使用者對資料的訪問許可權。
4.提供向後相容性:檢視使使用者能夠在表的架構更改時為表建立向後相容介面。
5.自定義資料:檢視允許使用者以不同方式檢視資料。
6.匯出和匯入資料:可使用檢視將資料匯出到其他應用程式。
 
三.how(檢視的建立語法、刪除、demo)

CREATE [OR REPLACE] [FORCE|NOFORCE] VIEW view_name

[(alias[, alias]...)]

AS subquery

[WITH CHECK OPTION [CONSTRAINT constraint]]

[WITH READ ONLY]


OR REPLACE :若所建立的試圖已經存在,ORACLE自動重建該檢視;
FORCE :不管基表是否存在ORACLE都會自動建立該檢視;
NOFORCE :只有基表都存在ORACLE才會建立該檢視:
alias :為檢視產生的列定義的別名;
subquery :一條完整的SELECT語句,可以在該語句中定義別名;
WITH CHECK OPTION :插入或修改的資料行必須滿足檢視定義的約束;
WITH READ ONLY :該檢視上不能進行任何DML操作。


CREATE OR REPLACE VIEW dept_sum_vw
(name,minsal,maxsal,avgsal)
AS
SELECT d.dname,min(e.sal),max(e.sal),avg(e.sal)
FROM emp e,dept d
WHERE e.deptno=d.deptno
GROUP BY d.dname;


--給使用者授權建立檢視
-- grant create all view to zdgshr; 所有資料庫都能建立檢視的使用者
grant create view to zdgshr;

--建立簡單檢視
create view temp
as
select * from zd_member_basic_info;
--測試
select * from temp where rownum=1;

--建立簡單檢視:只讀
create or replace view temp1
as
select id,job_number,name,dept_id from zd_member_basic_info
with read only;
--測試
insert into temp1(id,job_number,name,dept_id) values(1,0,'張三',1300);

檢視的刪除:

            DROP VIEW  VIEW_NAME語句刪除檢視。
            刪除檢視的定義不影響基表中的資料。
            只有檢視所有者和具備DROP VIEW許可權的使用者可以刪除檢視。
            檢視被刪除後,基於被刪除檢視的其他檢視或應用將無效。
 

四、檢視分為簡單檢視和複雜檢視。

簡單檢視只從單表裡獲取資料;複雜檢視從多表裡獲取資料。

簡單檢視不包含函式和資料組;複雜檢視包含函式和資料組。

簡單檢視可以實現DML操作;複雜檢視不可以。

create or replace view temp1
as
select distinct name,job_number,dept_id from zd_member_basic_info
with read only;
delete from zd_member_basic_info where name='而過';
create or replace view temp
as
select * from zd_member_basic_info order by name;

oracleview檢視更新建立 
 
檢視是從一個表或檢視匯出的表,也可以是從多個表或檢視匯出的表。檢視是一個虛表,資料庫不對檢視所對應的資料進行實際儲存,只儲存檢視的定義,對檢視的資料進行操作時,系統根據檢視的定義去操作與檢視相關聯的基表。
檢視一旦被定義以後就可以像表一樣被查詢、修改、刪除和更新。
使用檢視有如下優點:
(1)為使用者集中資料,簡化使用者的資料查詢和處理。有時我們所需要的資料可能分散在幾個不同的表中,定義檢視可以將它們集中在一起,從而方便我們對資料的查詢和處理。
(2)遮蔽資料庫的複雜性。在使用資料時,使使用者不必瞭解複雜的資料庫表結構。
(3)簡化使用者的許可權管理。我們有時候可能會授予某一使用者只能檢視對應表的某些列,這是相當麻煩的,有了檢視後,我們就可以把能夠檢視的列抽出來建立對應的檢視,然後賦予使用者使用檢視的許可權。
(4)便於資料共享。各不同的使用者不必都儲存自己的資料,同樣的資料只需儲存一次。


1、使用create view語句建立檢視:
語法格式:
 
Sql程式碼  
    create [or replace] [force | noforce] view [schema.]viewName[(columnName[,...n])]  
        as selectStatement [with check option[constraint constraintName]]  
            [with read only]  
--or replace表示如果對應名稱的檢視已經存在,則重建該檢視,即把原來的檢視銷燬,再重建對應的檢視。  
--force表示強制建立一個檢視,無論檢視的基表是否存在或擁有者是否有許可權。  
--columnName是檢視中包含的列,可以有多個列名。若使用與源表或檢視相同的列名,則不必給出columnName,但以下情況則必須指出列名:  
--(1)由算術表示式、系統內建函式或者常量得到的列  
--(2)共享同一個表名得到的列  
--(3)希望檢視中的列名與基表的列名不同的時候  
--selectStatement表示用於建立檢視的select語句,可在select語句中查詢多個表或檢視。  
--with check option指出在檢視上所進行的修改都要符合selectStatement所指定的限制條件,這樣可以保證資料修改後,仍可通過檢視檢視修改的資料。  
--with read only指定檢視中不能進行刪除、更新和插入操作,只能進行檢索操作。  
 
示例程式碼:
 
Sql程式碼  
create or replace view personView as select name,sex from person with read only; --對person表的name和sex列建立只讀檢視。  
create or replace view personView(sex,平均年齡) as select sex, avg(age) from person group by sex with check option;  
--對person表中的性別進行分組,得出男女的平均年齡,並建立檢視,檢視的列名改為sex和平均年齡。  
 

2、查詢檢視
檢視定義後,就可以對檢視進行查詢了,檢視的查詢跟對基表的查詢是一樣的。
示例程式碼:
 
Sql程式碼  
select * from personView; --該語句就會查出檢視personView裡面的所有欄位  
 
使用檢視查詢時,如果基表中增加了新的欄位,那麼只有在重建檢視後才能在新的檢視中查詢到新增加的欄位。例如:假設有一個表person(id,name,sex),對該表建立了檢視personView(create or replace view personView as select * from person),如果之後我給person新增加了一個age欄位,那麼在這個時候我呼叫查詢(select * from personView)的結果集中是不包含age欄位的,如果想顯示age欄位,則需要重建該檢視。這個原因就是之前說過的檢視只是一個虛表,建立檢視的時候在資料字典裡面只儲存了檢視的定義,在對檢視進行操作的時候,系統會根據檢視的定義去操作對應的基表,所以在基表裡面新增了欄位之後,對應的檢視中是沒有新欄位的定義的,也就不能顯示新欄位了。
如果與檢視相關聯的表或者檢視被刪除,則該檢視將不能再使用。


3、更新檢視
通過更新檢視,可以修改基表中的資料。但並不是所有的檢視都是可以進行更新的,一個檢視能夠更新需要滿足以下條件:
a.沒有使用連線函式、集合運算函式和組函式
b.建立檢視的select語句中沒有聚合函式且沒有group by、start with子句和distinct關鍵字
c.建立檢視沒有包含只讀屬性
(1)插入資料
可以使用insert語句通過檢視向基表插入資料
示例程式碼:
 
Sql程式碼  
--假設有這樣一個檢視:create or replace view personView as select name, sex from person;  
    insert into personView values('張三', '男'); --personView是對應的檢視名。  
 
(2)修改資料
可以使用update語句通過檢視修改基表中的資料,操作和修改表資料差不多。
示例程式碼:
 
Sql程式碼  
update personView set sex='女' where name='張三';  
 
(3)刪除資料
可以使用delete語句通過檢視刪除基表中的資料。
示例程式碼:
 
Sql程式碼  
delete from personView where name='張三';  
 


4、修改檢視的定義 ---需要補充
Oracle中提供了alter view語句,但是該語句不是用於修改檢視的定義的,而是用於重新編譯或者驗證現有檢視的。修改檢視的定義的方法和新建檢視的方法差不多,只是使用的是create or replace view viewName……,這樣新的檢視就代替了舊的檢視了。
示例程式碼:
--修改檢視personView的定義
 
Sql程式碼  
create or replace force view personView as select id,name,age from person;  
 
 
 
5、刪除檢視
刪除檢視就是刪除檢視的定義,刪除一個檢視是相當簡單,類似於刪除一個表,它的語法格式如下:
drop view [schema.]viewName;

Oracle之物化檢視

近期根據專案業務需要對oracle的物化檢視有所接觸,在網上搜尋關於這方面的資料,便於提高,整理內容如下:

物化檢視是一種特殊的物理表,“物化”(Materialized)檢視是相對普通檢視而言的。普通檢視是虛擬表,應用的侷限性大,任何對檢視的查詢,Oracle都實際上轉換為檢視SQL語句的查詢。這樣對整體查詢效能的提高,並沒有實質上的好處。
1、物化檢視的型別:ON DEMAND、ON COMMIT

    二者的區別在於重新整理方法的不同,ON DEMAND顧名思義,僅在該物化檢視“需要”被重新整理了,才進行重新整理(REFRESH),即更新物化檢視,以保證和基表資料的一致性;而ON COMMIT是說,一旦基表有了COMMIT,即事務提交,則立刻重新整理,立刻更新物化檢視,使得資料和基表一致。
2、ON DEMAND物化檢視   

物化檢視的建立本身是很複雜和需要優化引數設定的,特別是針對大型生產資料庫系統而言。但Oracle允許以這種最簡單的,類似於普通檢視的方式來做,所以不可避免的會涉及到預設值問題。也就是說Oracle給物化檢視的重要定義引數的預設值處理是我們需要特別注意的。   

物化檢視的特點:

     (1) 物化檢視在某種意義上說就是一個物理表(而且不僅僅是一個物理表),這通過其可以被user_tables查詢出來,而得到佐證;

    (2) 物化檢視也是一種段(segment),所以其有自己的物理儲存屬性;

     (3) 物化檢視會佔用資料庫磁碟空間,這點從user_segment的查詢結果,可以得到佐證;

    建立語句:create materialized view mv_name as select * from table_name    預設情況下,如果沒指定重新整理方法和重新整理模式,則Oracle預設為FORCE和DEMAND。
    物化檢視的資料怎麼隨著基表而更新?    Oracle提供了兩種方式,手工重新整理和自動重新整理,預設為手工重新整理。也就是說,通過我們手工的執行某個Oracle提供的系統級儲存過程或包,來保證物化檢視與基表資料一致性。這是最基本的重新整理辦法了。自動重新整理,其實也就是Oracle會建立一個job,通過這個job來呼叫相同的儲存過程或包,加以實現。

       ON DEMAND物化檢視的特性及其和ON COMMIT物化檢視的區別,即前者不重新整理(手工或自動)就不更新物化檢視,而後者不重新整理也會更新物化檢視,——只要基表發生了COMMIT。

    建立定時重新整理的物化檢視:create materialized view mv_name refresh force on demand start with sysdate next sysdate+1 (指定物化檢視每天重新整理一次)

     上述建立的物化檢視每天重新整理,但是沒有指定重新整理時間,如果要指定重新整理時間(比如每天晚上10:00定時重新整理一次):create materialized view mv_name refresh force on demand start with sysdate next to_date( concat( to_char( sysdate+1,'dd-mm-yyyy'),' 22:00:00'),'dd-mm-yyyy hh24:mi:ss')
3、ON COMMIT物化檢視

     ON COMMIT物化檢視的建立,和上面建立ON DEMAND的物化檢視區別不大。因為ON DEMAND是預設的,所以ON COMMIT物化檢視,需要再增加個引數即可。   需要注意的是,無法在定義時僅指定ON COMMIT,還得附帶個引數才行。

     建立ON COMMIT物化檢視:create materialized view mv_name refresh force on commit as select * from table_name    備註:實際建立過程中,基表需要有主鍵約束,否則會報錯(ORA-12014)

4、物化檢視的重新整理

     重新整理(Refresh):指當基表發生了DML操作後,物化檢視何時採用哪種方式和基表進行同步。重新整理的模式有兩種:ON DEMAND和ON COMMIT。(如上所述)

     重新整理的方法有四種:FAST、COMPLETE、FORCE和NEVER。FAST重新整理採用增量重新整理,只重新整理自上次重新整理以後進行的修改。COMPLETE重新整理對整個物化檢視進行完全的重新整理。如果選擇FORCE方式,則Oracle在重新整理時會去判斷是否可以進行快速重新整理,如果可以則採用FAST方式,否則採用COMPLETE的方式。NEVER指物化檢視不進行任何重新整理。

      對於已經建立好的物化檢視,可以修改其重新整理方式,比如把物化檢視mv_name的重新整理方式修改為每天晚上10點重新整理一次:alter materialized view mv_name refresh force on demand start with sysdate next to_date(concat(to_char(sysdate+1,'dd-mm-yyyy'),' 22:00:00'),'dd-mm-yyyy hh24:mi:ss')   
5、物化檢視具有表一樣的特徵,所以可以像對錶一樣,我們可以為它建立索引,建立方法和對錶一樣。
6、物化檢視的刪除:

      雖然物化檢視是和表一起管理的,但是在經常使用的PLSQL工具中,並不能用刪除表的方式來刪除(在表上右鍵選擇‘drop’並不能刪除物化檢視),可以使用語句來實現:drop materialized view mv_name 

物化檢視建立引數

 (1)BUILD BUILD IMMEDIATE 是在建立物化檢視的時候就生成資料 BUILD DEFERRED 則在建立時不生成資料,以後根據需要再生成資料。 預設為BUILD IMMEDIATE。
(2)REFRESH FAST 增量重新整理用物化檢視日誌,來傳送主表已經修改的資料行到物化檢視中。 COMPLETE 完全重新整理重新生成整個檢視,如果請求完全重新整理,oracle會完成完全重新整理即使增量重新整理可用。 FORCE 如果增量重新整理可用Oracle將完成增量重新整理,否則將完成完全重新整理,如果不指定重新整理方法(FAST, COMPLETE, or FORCE)。 預設選項是Force。
(3)ON ON DEMAND 指物化檢視在使用者需要的時候進行重新整理。 ON COMMIT 指出物化檢視在對基表的DML操作提交的同時進行重新整理。 預設是ON DEMAND.
(4)START WITH 通知資料庫完成從主表到本地表第一次複製的時間。
(5)NEXT 說明了重新整理的時間間隔 根據下一次重新整理的時間=上一次執行完成的時間+時間間隔。 為了保證在使用者需要的時間點重新整理,一般使用TRUNC()命令對時間取整到天數,然後加上時間。

具體示例程式碼如下所示:


/* Formatted on 2012/3/28 11:26:08 (QP5 v5.149.1003.31008) */
--刪除日誌
TRUNCATE TABLE mlog$_fe_fee;
DROP MATERIALIZED VIEW LOG ON fe_fee;
TRUNCATE TABLE mlog$_fe_order;
DROP MATERIALIZED VIEW LOG ON fe_order;
TRUNCATE TABLE mlog$_fe_job;
DROP MATERIALIZED VIEW LOG ON fe_job;
TRUNCATE TABLE mlog$_fi_acc_bill;
DROP MATERIALIZED VIEW LOG ON fi_acc_bill;
TRUNCATE TABLE mlog$_fi_acc_fee;
DROP MATERIALIZED VIEW LOG ON fi_acc_fee;
TRUNCATE TABLE mlog$_fe_fee_age;
DROP MATERIALIZED VIEW LOG ON fe_fee_age;

--建立基表日誌
CREATE MATERIALIZED VIEW LOG ON fe_fee WITH ROWID, SEQUENCE(job_id, order_id) INCLUDING NEW VALUES;
CREATE MATERIALIZED VIEW LOG ON fe_order WITH ROWID, SEQUENCE( order_id)INCLUDING NEW VALUES;
CREATE MATERIALIZED VIEW LOG ON fe_job WITH ROWID ,SEQUENCE(job_id)INCLUDING NEW VALUES;
CREATE MATERIALIZED VIEW LOG ON fi_acc_bill WITH ROWID, SEQUENCE(bill_id) INCLUDING NEW VALUES;
CREATE MATERIALIZED VIEW LOG ON fi_acc_fee WITH ROWID, SEQUENCE(fee_id) INCLUDING NEW VALUES;
CREATE MATERIALIZED VIEW LOG ON fe_fee_age WITH ROWID, SEQUENCE(job_id, order_id) INCLUDING NEW VALUES;

--建立物化檢視
DROP MATERIALIZED VIEW mv_job_fee;


CREATE MATERIALIZED VIEW mv_job_fee
BUILD IMMEDIATE
REFRESH FAST
ON DEMAND
START WITH SYSDATE
NEXT SYSDATE + 5/(60*24)
AS
SELECT f.ROWID fi, j.ROWID ji, o.ROWID oi, b.ROWID bi, c.ROWID ci, f.fee_id,
f.job_id, f.order_id, f.fee_type, f.fee_code, f.unit_price, f.quantity,
f.currency, f.fx_rate, f.cust_id, f.invoice_num, f.is_confirm,
f.blunt_flag, f.verify_balance, f.is_agreement, f.fiscal_period,
f.attribute, f.continue, f.remark, f.security, f.create_by,
f.create_time, f.pay_type, f.sharing_type, f.bill_id, f.direction,
f.profit_loses, f.unit, f.relation_cust, f.amount, f.fx_amout,
f.modified_by, f.modified_date, f.proportion, f.job_period,
o.quantity ord_quantity, o.gross_weight ord_gross_weight,
o.volume ord_volume, o.charge_weight ord_charge_weight,
o.custom_num ord_custom_num, o.pay_type ord_pay_type,
o.pay_type2 ord_pay_type2, o.teu ord_teu,
o.cust_service ord_cust_service, o.oper ord_oper, o.bill ord_bill,
o.sales ord_sales, o.cust_id ord_cust_id, o.bill_no bill_no , 1 AS ord_canvassing,1 AS ord_agent_type,
j.dept_id job_dept_id,
j.job_type job_job_type, j.firm job_firm, j.way_bill job_way_bill,
j.loading job_loading, j.discharging job_discharging, j.etd job_etd,
j.eta job_eta, j.flight_num job_flight_num, j.provider job_provider,
j.carrier job_carrier, j.voyage job_voyage, j.quantity job_quantity,
j.gross_weight job_gross_weight, j.volume job_volume,
j.charge_weight job_charge_weight, j.teu job_teu,
j.fee_lock job_fee_lock, j.lock_time job_lock_time,
j.auditor job_auditor, j.archiveno job_archiveno,
j.archived_by job_archived_by, j.archived_time job_archived_time,
j.oversea_agent job_oversea_agent, j.container_info job_container_info,
j.container_num job_container_num, j.proj_id job_proj_id,
j.route job_route,
b.book_date bill_book_date, b.commit_flag bill_commit_flag,
b.pay_period bill_pay_period, b.invoice_rise, c.confirm_amount,
c.confirm_time
FROM fe_fee f, fe_order o, fe_job j, fi_acc_bill b, fi_acc_fee c
WHERE f.job_id = j.job_id(+)
AND f.order_id = o.order_id(+)
AND f.bill_id = b.bill_id(+)
AND f.fee_id = c.fee_id(+);


DROP MATERIALIZED VIEW mv_order_cargo;

CREATE MATERIALIZED VIEW mv_order_cargo
BUILD IMMEDIATE
REFRESH FAST
ON DEMAND
START WITH SYSDATE
NEXT SYSDATE + 10/(60*24)
AS
SELECT j.ROWID ji, o.ROWID oi, o.order_id, o.job_type, o.cust_id, o.dept_id,
o.firm, o.job_id, o.quantity, o.gross_weight, o.volume,
o.charge_weight, o.custom_num, j.loading, j.discharging, o.pay_type,
o.pay_type2, o.teu, o.cust_service, o.oper, o.bill, o.sales,
o.booking_type, o.route, o.assign_agent, j.way_bill, j.etd, j.eta,
j.flight_num, j.provider, j.carrier, j.voyage, j.quantity job_quantity,
j.gross_weight job_gross_weight, j.volume job_volume,
j.charge_weight job_charge_weight, j.teu job_teu, j.job_period,
j.oversea_agent, j.container_info, j.container_num
FROM fe_order o, fe_job j
WHERE o.job_id = j.job_id(+);

DROP MATERIALIZED VIEW mv_fee_age;

CREATE MATERIALIZED VIEW mv_fee_age
BUILD IMMEDIATE
REFRESH FAST
ON DEMAND
START WITH SYSDATE
NEXT SYSDATE + 5/(60*24)
AS
SELECT a.ROWID ai, f.ROWID fi, j.ROWID ji, o.ROWID oi, a.fee_id,
a.job_id, a.order_id, f.fee_type, f.fee_code, f.unit_price, f.quantity,
f.currency, f.fx_rate, f.cust_id, f.invoice_num, f.is_confirm,
f.blunt_flag, f.verify_balance, f.is_agreement, f.fiscal_period,
f.attribute, f.continue, f.remark, f.security, f.create_by,
f.create_time, f.pay_type, f.sharing_type, f.bill_id, f.direction,
f.profit_loses, f.unit, f.relation_cust, f.amount, f.fx_amout,
f.modified_by, f.modified_date, f.proportion, f.job_period,
o.quantity ord_quantity, o.gross_weight ord_gross_weight,
o.volume ord_volume, o.charge_weight ord_charge_weight,
o.custom_num ord_custom_num, o.pay_type ord_pay_type,
o.pay_type2 ord_pay_type2, o.teu ord_teu,
o.cust_service ord_cust_service, o.oper ord_oper, o.bill ord_bill,
o.sales ord_sales, o.cust_id ord_cust_id, j.dept_id job_dept_id,
j.job_type job_job_type, j.firm job_firm, j.way_bill job_way_bill,
j.loading job_loading, j.discharging job_discharging, j.etd job_etd,
j.eta job_eta, j.flight_num job_flight_num, j.provider job_provider,
j.carrier job_carrier, j.voyage job_voyage, j.quantity job_quantity,
j.gross_weight job_gross_weight, j.volume job_volume,
j.charge_weight job_charge_weight, j.teu job_teu,
j.fee_lock job_fee_lock, j.lock_time job_lock_time,
j.auditor job_auditor, j.archiveno job_archiveno,
j.archived_by job_archived_by, j.archived_time job_archived_time,
j.oversea_agent job_oversea_agent, j.container_info job_container_info,
j.container_num job_container_num, j.proj_id job_proj_id
FROM fe_fee_age a, fe_fee f, fe_order o, fe_job j
WHERE a.fee_id = f.fee_id(+)
AND a.job_id = j.job_id(+)
AND a.order_id = o.order_id(+);


v$database :displays information about the database from the control file.
v$instance :displays the state of the current instance(當前例項的狀況)
v$option :displays oracle database options and features(資料庫的選項和特性)
         :option must be separately licensed(選項單獨認證設定)
         :whereas features come with the product and are enabled based on
          the product that is running(產品特性的發揮也是要產品執行才能體現)
v$parameter :displays information about the initialization parameter that
            :are currently in effect for the session.A new session inherits
            :parameter values from the instance-wide values displayed by the
            :v$system_parameter view.
v$backup    :display the backup status of all online datafiles.(所有線上資料檔案的備份情況)
v$px_process_sysstat :contains information about the sessions running parallel execution
                       (包含並行執行會話的資訊)
v$process :displays information about the currently active processes(活動程式的資訊)
v$waitstat: displays block contention statistics.this table is only updated when timed
          :statistics are enabled(顯示熱塊競爭的統計,當時間統計引數啟動時,這個表只能更新)
v$system_event :total waits for an event(事件的總等待時間)
 
2.關於磁碟檔案的檢視
v$datafile :datafile information from the control file
v$filestat :displays the number of physical reads and writes done and the total number of
         :single-block and multiblock I/Os done at file level(在檔案級別顯示物理讀寫和io資訊)
v$log    :displays log file information from the control file
v$log_history :log history information from the control file
v$dbfile :all datafiles making up the database
v$tempfile :tempfile information
v$tempstat :file read/write statistics(檔案讀寫的統計)
v$segment_statistics :segment-level statistics
 
3.contention競爭的檢視
v$lock :lists the locks currently held by the oracle database and outstanding requests for
       : a lock or latch (正在使用的鎖和過多的請求對鎖)
v$rollname :lists the names of all online rollback segments(線上回滾段的資訊)
v$rollstat :contains rollback segment statistics(回滾段的統計情況)
v$waitstat :block contention statistics(塊爭用統計)
v$latch :aggregate latch statistics (閂鎖的總和統計)
 
4.memory 的檢視
v$buffer_pool_statistics :statistics about all buffer pools available for the instance
                         :(例項所有可用的快取池的統計)
v$db_object_cache:database objects thatare cached inthe library cache(被快取在庫快取區的物件)
v$librarycache :contains statistics about library cache performance and activity
               (庫快取區的效能和活動的統計資訊)
v$rowcache :statistics for data dictionary activity(資料字典活動資訊統計)
v$sysstat:system statistics
v$sgastat :detailed information on the system global area(sga)
 
5.使用者/會話的檢視
v$lock :lists the locks currently held by the oracle database and outstanding requests for
       : a lock or latch (正在使用的鎖和過多的請求對鎖)
v$open_cursor :list cursors that each user session currently has opened and parsed,or cached
               (當前會話開啟的遊標列表)
v$process :displays information about the currently active processes(活動程式的資訊)
v$transaction :lists the active transaction in the system (列出系統活動的事物)
v$px_sesstat :parallel execution(px),contains information about the sessions running
              (正在執行會話的並行執行情況統計)
v$px_session :parallel execution(px),contains information about the sessions running
v$sesstat :user session statistics
v$session_event :on waits for an event by a session(會話等待事件)
v$sort_usage :在11g好像就沒有了
v$sort_segment:displays information about every sort segment in given instance
               顯示例項中給出的每個回滾段的資訊。
v$session_wait :current or last wait for each session(當前或上次的等待資訊)
v$session
v$session_object_cache :object cache statistics for the current user session on the local 
                       :server(instance)

相關文章