国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 數(shù)據(jù)庫 > Oracle > 正文

ORACLE數(shù)據(jù)庫PROC編程經(jīng)驗介紹

2024-08-29 13:38:45
字體:
供稿:網(wǎng)友

  PROC是Oracle數(shù)據(jù)庫提供的編程接口之一,其應(yīng)用十分的廣泛,本文通過一個具體的例子,介紹PROC編程的一些經(jīng)驗及應(yīng)注重的地方。
  
  例子程序:
  #include
  #include
  #include
  #include
  #include
  
  
  EXEC SQL INCLUDE sqlca;
  /*RELEASE_CURSOR=YES 使PROC 在執(zhí)行完后釋放與嵌入SQL有關(guān)資源*/
  EXEC ORACLE OPTION (RELEASE_CURSOR = YES);
  
  EXEC SQL BEGIN DECLARE SECTION;
  varchar vc_user[20];
  long al_empno=0;
  char ac_ename[11]="";
  char ac_hiredate[20]="";
  double af_sal=0;
  
  EXEC SQL VAR ac_ename IS STRING(11);
  EXEC SQL VAR ac_hiredate IS STRING(20);
  
  EXEC SQL END DECLARE SECTION;
  
  
  /*錯誤處理函數(shù)*/
  void sql_error(char *msg)
  {
  printf("/n%s,%ld,%s/n", msg,sqlca.sqlcode,(char *)sqlca.sqlerrm.sqlerrmc);
  EXEC SQL ROLLBACK RELEASE;
  exit(-1);
  }
  
  
  main()
  {
  EXEC SQL WHENEVER SQLERROR DO sql_error("ORACLE ERROR: ");
  
  /*連接數(shù)據(jù)庫*/
  strcpy(vc_user.arr,"scott/tiger@DEMO");
  vc_user.len=16;
  exec sql connect :vc_user;
  
  EXEC SQL DECLARE cur_emp CURSOR FOR
  SELECT EMPNO, ENAME,to_char(HIREDATE,'yyyy/mm/dd hh24:mi:ss'),SAL FROM EMP;
  
  EXEC SQL OPEN cur_emp;
  while(1)
  {
  al_empno=0;
  strcpy(ac_ename,"");
  strcpy(ac_hiredate,"");
  af_sal=0;
  EXEC SQL FETCH cur_emp INTO :al_empno, :ac_ename:ename_ind, :ac_hiredate:hiredate_ind, :af_sal:sal_ind;
  if( sqlca.sqlcode == 1403)
  {
  break;
  }
  printf("empno=%ld,ename=%s,hiredate=%s,sal=%lf/n",al_empno,ac_ename,ac_hiredate,af_sal);
  }
  EXEC SQL CLOSE cur_emp;
  EXEC SQL ROLLBACK WORK RELEASE;
  }
  
  
  
  1、宿主變量的聲明
  在PROC中,在SQL語句中用到的變量稱為宿主變量。他們應(yīng)在EXEC SQL BEGIN DECLARE SECTION;與EXEC SQL EDN DECLARE SECTION;
  之間聲明,如上面所示.在聲明宿主變量時應(yīng)注重以下幾點:
  (1) 在數(shù)據(jù)庫表中定義為VARCHAR2,VARCHAR,CHAR的字段,在PROC中可聲明為CHAR,但長度應(yīng)為它們在表中定義的長度加1,因為PROC中
  CHAR型變量用/0做結(jié)尾。
  
  如:ENAME在表中的定義為ename varchar2(10),在PROC中可定義為:
  EXEC SQL BEGIN DECLARE SECTION;
  char ename[11];
  EXEC SQL END DECLARE SECTION;
  常見錯誤說明:
  假如插入的字符串長度大于10,如:EXEC SQL INSERT INTO EMP(ENAME) VALUES('12345678901');會出現(xiàn)以下錯誤:
  error:ORA-01480: STR 賦值變量缺少空后綴。
  
  假如定義為:
  EXEC SQL BEGIN DECLARE SECTION;
  char ename[15];
  EXEC SQL END DECLARE SECTION;
  
  當插入的字符串長度大于10,小于15時,如:EXEC SQL INSERT INTO EMP(ENAME) VALUES('12345678901');會出現(xiàn)以下錯誤:
  error:ORA-01401: 插入的值對于列過大。

  當插入的字符串長度大于15,如:EXEC SQL INSERT INTO EMP(ENAME) VALUES('12345678901234');會出現(xiàn)以下錯誤:
  error:ORA-01401:STR 賦值變量缺少空后綴。
  
  (2) 從SQL語句中取字段的值到宿主變量中時,PROC不會自動給宿主變量去掉右空格。而是以在DECLARE SECTION 中定義的長度為準(與 表中定義的無關(guān))不足補右空格.假如不注重這一點,在PROC中進行字符串操作時(如比較相等)會出錯。如:
  EXEC SQL BEGIN DECLARE SECTION;
  char ename[10];
  EXEC SQL END DECLARE SECTION;
  假如ENAME在表中的值為'abc',則取出的值為'abc ';
  
  可用語句EXEC SQL VAR重定義CHAR型變量。這樣宿主變量會自動去掉右空格。如下:
  EXEC SQL BEGIN DECLARE SECTION;
  char ename[11];
  EXEC SQL VAR ac_ename IS STRING(11);
  EXEC SQL END DECLARE SECTION;
  假如ENAME在表中的值為'abc',則取出的值為'abc';
  
  (3) 對浮點型的變量,為保證精度,最好是聲明成DOUBLE型的.因為DOUBLE型的精度比FLOAT型高很多.
  (4) 整型可聲明為LONG型(對較長的整型,而且所用的平臺支持的話,如在SUN平臺上,可聲明為LONG LONG型).
  (5) DATE型的處理:DATE型一般聲明為CHAR(20)。
  往表中插入DATE型數(shù)據(jù)時,一般用TO_DATE()函數(shù)進行類型轉(zhuǎn)換,取出值時一般用TO_CHAR()函數(shù)進行類型轉(zhuǎn)換.
  EXEC SQL select to_char(hiredate,'yyyy/mm/dd hh24:mi:ss') into :ac_hire_date from EMP where empno=1234;
  EXEC SQL insert into EMP(EMPNO,HIREDATE) values(123,to_date(:ac_hiredate,'yyyy/mm/dd hh24:mi:ss');
  
  
  2、宿主變量的作用范圍
  假如宿主變量在所有的函數(shù)之外聲明,則他們是全局變量。在使用之前要注重把變量的值初始化,宿主變量也可以在某個函數(shù)的內(nèi)部定義。 這時他們是局部變量。一般都習慣把宿主變量聲明為全局變量。
  
  3、數(shù)據(jù)庫的連接與斷開
  數(shù)據(jù)庫的連接有以下兩種方法:
  (1)
  strcpy(vc_user.arr,"scott/tiger");
  vc_user.len=11;
  exec sql connect :vc_user;
  (2)
  strcpy(user,"scott");
  strcpy(pass,"tiger");
  exec sql connect :user identified by :pass;
  注重:在有些平臺上兩種都可以,在有些平臺上只能用第一種方法.
  在PROC程序中,要記住用EXEC SQL ROLLBACK WORK RELEASE;斷開與數(shù)據(jù)庫的連接,并釋放相關(guān)的數(shù)據(jù)庫資源。
  
  
  4、PROC中的NULL值的處理
  假如某一字段取出的值是NULL,會報:sqlcode=-1405, sqlerr=ORA-01405: 讀取的列值為 NULL
  并且相應(yīng)的宿主變量的值不會被改變,為執(zhí)行該SQL語句之前的值. 常用的處理NULL值的方法有:
  (1)采用指示器變量,此時不會有-1405錯誤,當必須是所以為NULL的字段都有相應(yīng)的指示器變量,假如某一字段沒有指示器變量,但取出的值
  為NULL值,則仍然會有-1405錯誤.當取出的值是NULL時,相應(yīng)的指示器變量變量為-1,可根據(jù)指示器變量的值做響應(yīng)的處理。
  (2)假如字段較多,可取字段到一個結(jié)構(gòu)體中及與該結(jié)構(gòu)體對應(yīng)的指示器結(jié)構(gòu)體中.如上面的例子中可定義結(jié)構(gòu)體:
  strUCt str_emp{
  long al_empno;
  char ac_ename;
  char ac_hiredate;
  double af_sal;
  };
  struct str_emp_ind{
  long al_empno;
  char ac_ename;
  char ac_hiredate;
  double af_sal;
  };
  
  struct str_emp str_emp;
  strcut str_emp_ind str_emp_ind;
  在取之前可用memset(&str_emp,0,sizeof(str_emp)).清空該結(jié)構(gòu)體,這樣假如是字符型的NULL,會為"",整型的NULL會為0,
  浮點型的會為0.00。此時不會有-1405錯誤。
  (3)也可采用NVL()函數(shù):舉例如下:
  EXEC SQL DECLARE authors CURSOR FOR
  SELECT EMPNO, NVL(ENAME,chr(0)),nvl(to_char(HIREDATE,'yyyy/mm/dd hh24:mi:ss'),chr(0)),NVL(SAL,0) FROM EMP;
  這樣也不會有-1405錯誤不,當取出的值是NULL時,自動用NVL()中指定的值代替.
  CHR(0)也可直接用''代替,如下:
  SELECT EMPNO, NVL(ENAME,''),nvl(to_char(HIREDATE,'yyyy/mm/dd hh24:mi:ss'),''),NVL(SAL,0) FROM EMP;
  
  
  5、PROC中的錯誤的處理
  所有的SQL語句都有可能出錯.所以都要加以判定,但每個SQL語句后都加錯誤判定,太麻煩,可用一個函數(shù)如sql_error()來進行錯誤處理,
  方法:
  (1)定義ql_error()函數(shù)。

  (2)在開頭加上EXEC SQL WHENEVER SQLERROR DO sql_error();這樣當發(fā)生sqlca.sqlcode <0 的錯誤時,程序自動轉(zhuǎn)到sql_error()中執(zhí)行. 注重:對sqlca.sqlcode >0的錯誤如 sqlca.sqlcode =1403 是不會轉(zhuǎn)到sql_error()中執(zhí)行的.
  另外:在UNIX下,可以用OERR 來查找錯誤的描述。如: ora ORA -1405 查找錯誤號為-1405的描述.
  
  
  6、PROC中調(diào)用存儲過程的方法
  要把存儲過程放在EXEC SQL EXECUTE 和 END-EXEC;之間,如下所示:
  其中:al_empno,ac_ename 為輸入?yún)?shù),l_return,l_errno,c_errtext 為輸出參數(shù)。
  al_empno=8888;
  strcpy(ac_ename,"ABCD");
  EXEC SQL EXECUTE
  BEGIN
  up_db_emp(:al_empno,:ac_ename,:l_return,:l_errno,:c_errtext);
  END;
  END-EXEC;
  if (l_return != 0)
  {
  printf("調(diào)用UP_PB_EMP存儲過程出錯,errno=%ld,errtext=%s/n",l_errno,c_errtext);
  }
  
  7、PROC的命令行選項:PROC編譯器有很多的命令行選項,在命令行下直接不帶參數(shù)運行PROC,會列出所有的命令行選項來,并有說明。
  (1)儲存過程:編譯儲存過程是要帶上用戶名及密碼
  proc USERID=scott/tiger sqlcheck=SEMANTICS ireclen=512 iname=test.cpp
  (2)PARSE=NONE 對非SQL代碼不進行語法分析,默認對非SQL

發(fā)表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發(fā)表
主站蜘蛛池模板: 奉贤区| 贡嘎县| 金沙县| 白玉县| 宁波市| 十堰市| 五指山市| 长宁区| 新余市| 同江市| 宁安市| 固始县| 江源县| 辽宁省| 常熟市| 益阳市| 榕江县| 临沧市| 安平县| 竹北市| 松溪县| 东平县| 泰安市| 大冶市| 邯郸县| 芒康县| 彭阳县| 民丰县| 汉阴县| 三原县| 平凉市| 鹤峰县| 内江市| 醴陵市| 广汉市| 平罗县| 墨脱县| 威远县| 贵港市| 鲁甸县| 黄龙县|