動態為10g資料庫的表新增欄位,到256個欄位,hung住了?
ORACLE 10g單表最多是可以新增到1000個欄位的,但是資料量比較大時,使用procedure為表動態新增欄位,並對新新增的列執行相關操作,在新增到256個欄位時,該過程就停止了
create table customer_distcnty1 as select ideadata_id,customer_name from customer;--該表有11萬條資料,當選取2000條資料時,下面的過程可以順利完成
declare
cursor distcnty1_cursor is select * from distcnty1;
distcnty1_row distcnty1_cursor%rowtype;
distcnty_did distcnty1_row.did%type;
distcnty_name distcnty1_row.distcnty%type;
sqlstr1 varchar2(200);
sqlstr2 varchar2(200);
sqlstr3 varchar2(1000);
begin
for distcnty1_row in distcnty1_cursor loop
distcnty_did:=distcnty1_row.did;
distcnty_name:=distcnty1_row.distcnty;
cursor distcnty1_cursor is select * from distcnty1;
distcnty1_row distcnty1_cursor%rowtype;
distcnty_did distcnty1_row.did%type;
distcnty_name distcnty1_row.distcnty%type;
sqlstr1 varchar2(200);
sqlstr2 varchar2(200);
sqlstr3 varchar2(1000);
begin
for distcnty1_row in distcnty1_cursor loop
distcnty_did:=distcnty1_row.did;
distcnty_name:=distcnty1_row.distcnty;
--新增新列
sqlstr1:='alter table customer_distcnty1 add d'||distcnty_did||' varchar2(100)';
dbms_output.put_line(sqlstr1);
execute immediate sqlstr1;
sqlstr1:='alter table customer_distcnty1 add d'||distcnty_did||' varchar2(100)';
dbms_output.put_line(sqlstr1);
execute immediate sqlstr1;
--對新新增的列進行更新
sqlstr2:='update customer_distcnty1 set d'||distcnty_did||'=instr(customer_name,'''||distcnty_name||''')';
dbms_output.put_line(sqlstr2);
execute immediate sqlstr2;
sqlstr2:='update customer_distcnty1 set d'||distcnty_did||'=instr(customer_name,'''||distcnty_name||''')';
dbms_output.put_line(sqlstr2);
execute immediate sqlstr2;
--對新新增的列進行更新
sqlstr3:='update customer_distcnty1 set d'||distcnty_did||'=''0'' where d'||distcnty_did||'<>''0'' and substr(customer_name,instr(customer_name,'''||distcnty_name||''')+length('''||distcnty_name||'''),1)=''省'' and substr(customer_name,instr(customer_name,'''||distcnty_name||''')+length('''||distcnty_name||'''),1)=''市''';
dbms_output.put_line(sqlstr3);
execute immediate sqlstr3;
commit;
end loop;
end;
/
sqlstr3:='update customer_distcnty1 set d'||distcnty_did||'=''0'' where d'||distcnty_did||'<>''0'' and substr(customer_name,instr(customer_name,'''||distcnty_name||''')+length('''||distcnty_name||'''),1)=''省'' and substr(customer_name,instr(customer_name,'''||distcnty_name||''')+length('''||distcnty_name||'''),1)=''市''';
dbms_output.put_line(sqlstr3);
execute immediate sqlstr3;
commit;
end loop;
end;
/
嘗試手段:
1、kill掉該程式,手工為該表新增幾個欄位試試
orcl@ SYS> Select p.spid,a.serial#, c.object_name,b.session_id,b.oracle_username,b.os_user_name from v$process p,v$session a, v$locked_object b,all_objects c where p.addr=a.paddr and a.process=b.process and c.object_id=b.object_id;
SPID SERIAL# OBJECT_NAME SESSION_ID ORACLE_USERNAME OS_USER_NAME
------------ ---------- ------------------------------ ---------- ------------------------------ ------------------------------
18876 13339 CUSTOMER_DISTCNTY1 528 LENOVO oracle
------------ ---------- ------------------------------ ---------- ------------------------------ ------------------------------
18876 13339 CUSTOMER_DISTCNTY1 528 LENOVO oracle
Elapsed: 00:00:00.01
orcl@ SYS> alter system kill session '528,13339';
orcl@ SYS> alter system kill session '528,13339';
System altered.
Elapsed: 00:00:05.00
再對錶做如下操作時,發現都沒有問題
alter table CUSTOMER_DISTCNTY1 add test1 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test2 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test3 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test4 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test5 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test2 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test3 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test4 varchar2(100);
alter table CUSTOMER_DISTCNTY1 add test5 varchar2(100);
可見並不是無法新增表列。
2、試試執行過程中的第二條sql語句,對新增上的最後一列進行更新,發現對此列的更新超級的慢,這樣就可以鎖定原因是對列的更新使得程式hung住了。
那麼這種現象又是怎麼回事呢?是什麼原因導致執行update語句時程式停住呢,無疑是資料庫在進行比較大的操作。What is this?
3、由於新增的欄位都設定為varchar2(100),改成varchar2(3)試試如何。
結果無濟於事!
4、有可能是行的資料太大了,更新行時資料庫進行了行遷移。
可能又兩種解決辦法:1、減少表的列數2、使用非標準塊的表空間儲存該表
由於時間有限,在此就把大表拆成若干個小表來運算了,以後有時間可以嘗試非標準塊的表空間!
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/26613085/viewspace-740335/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- Python SqlAlchemy動態新增資料表欄位PythonSQL
- Mybatis框架:foreach迴圈遍歷欄位(為了解決動態表、動態欄位查詢資料)MyBatis框架
- SQL新增表欄位SQL
- 如何在水晶報表中動態新增欄位
- mysql資料庫新增和修改欄位MySql資料庫
- 位運算-設計資料庫表的多選狀態欄位資料庫
- 資料庫表欄位命名規範資料庫
- 如何較方便給上百張資料庫表新增表欄位資料庫
- MySQL中修改一個資料庫下包含有某個相同欄位的所有表的欄位長度MySql資料庫
- sqlserver查詢一個庫所有表的欄位名及欄位型別SQLServer型別
- 欄位管理,為什麼只有新增的時候才自動匹配欄位型別型別
- fastadmin 新增欄位記圖片欄位AST
- 資料庫索引欄位請不要為NULL資料庫索引Null
- 資料庫int欄位超限資料庫
- 資料庫欄位問題資料庫
- 觸發器—一個表插入資料時其他欄位同步自增長欄位觸發器
- mysql 資料庫 表 欄位 編碼修改 方法MySql資料庫
- mybatis動態呼叫表名和欄位名MyBatis
- ASP獲取資料庫表名,欄位名以及對欄位的一些操作 (轉)資料庫
- 將多個JSON欄位對映到單個Java欄位JSONJava
- 向資料庫中全部表中增加一個欄位的SQL資料庫SQL
- 在資料庫表中加一個狀態欄位可以代替軟刪除嗎?資料庫
- 為什麼資料庫欄位要使用NOT NULL?資料庫Null
- Oracle-欄位的新增Oracle
- oracle刪除表欄位和oracle表增加欄位Oracle
- MySQL 更新一個表裡的欄位等於另一個表某欄位的值MySql
- MySQL之資料庫和表的基本操作(建立表、刪除表、向表中新增欄位)MySql資料庫
- EF Core3.1 CodeFirst動態自動新增表和欄位的描述資訊
- 表中已有資料,將表中某個欄位為空的改為非空
- 對資料庫中的表或欄位重新命名資料庫
- oracle 資料庫設定表和欄位的別名Oracle資料庫
- 給mybatis新增自動建表,自動加欄位的功能MyBatis
- postgresql分割槽表修改資料表欄位SQL
- MySQL欄位新增註釋,但不改變欄位的型別MySql型別
- 序列化,資料庫存多個欄位資料資料庫
- Sql查詢 一個表中某欄位的資料在另一個表中某欄位中不存在的SQL
- 【Mongo】mongo更新欄位為另一欄位的值Go
- SQL Server中獲取資料庫名、表名、欄位名和欄位註釋的SQL語句SQLServer資料庫