Chinaunix首页 | 论坛 | 博客
  • 博客访问: 418658
  • 博文数量: 66
  • 博客积分: 1416
  • 博客等级: 上尉
  • 技术积分: 922
  • 用 户 组: 普通用户
  • 注册时间: 2006-09-16 10:37
个人简介

高級Oracle DBA,善長Linux系統維運以及Oracle數據庫管理,開發,調優. 具有多年PL/SQL開發經驗.

文章分类

全部博文(66)

文章存档

2015年(9)

2014年(4)

2013年(5)

2010年(1)

2009年(3)

2008年(6)

2007年(30)

2006年(8)

我的朋友

分类: Oracle

2013-12-26 11:25:53

 在我的工作中,经常需要访问Excel数据或者导入到oracle数据库中

常用的做法是:
   在前端程序中是逐行访问,读取数据.
   在oracle后端也可以处理.还更加方便

我封装了一个通用的package utl_excel.用来用SQL直接查询.

範例1:  excel数据存放在exceldata的blob_data栏位
   select  *
    from  exceldata a,
    table( utl_excel.get_xls_table(blob_data) ) xx
    where a.name='MSOFFICE.EXCEL';

範例2:  直接读取http或者ftp上的excel文件,    utl_lob是另外一个通用package
  select  *
    from    table(
             utl_excel.get_xls_table(utl_lob.url2blob('http://192.168.1.11/data/test.xls')  ) )


原理:
  java使用 jxl.jar 訪問excel ,用pl/sql封装成package

oracle 封装代碼如下,

点击(此处)折叠或打开

  1. CREATE OR REPLACE PACKAGE utl_excel authid definer as
  2. /****************************************************************************
  3.    Ver Date Author Description
  4.    --------- ---------- --------------- --------------------------------------------
  5.    1.0 2013-11-05 gangjh 1. 使用java jxl.jar 訪問blob的excel 2000數據.
  6.                                                返回table類型數據.
  7.                                                不支持xlsx,和ods格式
  8. *******************************************************************************/

  9.   SUBTYPE ctxHandle IS binary_integer;
  10.   subtype celltype is varchar2(4000 byte) ; -- limit for oracle 10g

  11.   SUBTYPE error_code_type IS BINARY_INTEGER;
  12.   SUBTYPE error_message_type IS VARCHAR2(1000);

  13.   type cell_val is record (
  14.   sheet int,
  15.   row_idx int,
  16.   col_idx int,
  17.   data celltype
  18.   ) ;
  19.   type xls_data is table of cell_val ;
  20.   c_max_cols constant pls_integer := 20;

  21.   type xls_row is record (
  22.     sheet int ,
  23.     row_idx int ,
  24.     col_a celltype,
  25.     col_b celltype,
  26.     col_c celltype,
  27.     col_d celltype,
  28.     col_e celltype,
  29.     col_f celltype,
  30.     col_g celltype,
  31.     col_h celltype,
  32.     col_i celltype,
  33.     col_j celltype,
  34.     col_k celltype,
  35.     col_l celltype,
  36.     col_m celltype,
  37.     col_n celltype,
  38.     col_o celltype,
  39.     col_p celltype,
  40.     col_q celltype,
  41.     col_r celltype,
  42.     col_s celltype,
  43.     col_t celltype
  44.   );
  45.   
  46.   type xls_table is table of xls_row ;
  47.   

  48. PROCEDURE raise_error_if_failure
  49.   (
  50.     error_code ERROR_CODE_TYPE,
  51.     error_message ERROR_MESSAGE_TYPE
  52.   ) ;


  53.  function number_to_date(v number) return date ;

  54. /****************************************
  55.  with xt as
  56. ( select a.id,a.name ,xx.*
  57.     from xmldata a,
  58.     table( utl_excel.get_xls_val(blob_temp) ) xx
  59.     where a.name='MSOFFICE.EXCEL'
  60. )

  61. select id,name,sheet,row_idx,
  62. max(decode(col_idx,0,data,'')) col0,
  63. max(decode(col_idx,1,data,'')) col1,
  64. max(decode(col_idx,2,data,'')) col2
  65. from xt
  66. group by id,name,sheet,row_idx;
  67. ************************/
  68.   
  69.   function get_xls_val(data in blob) RETURN xls_data PIPELINED ;


  70. /*********************************************
  71. ex1:
  72.   select a.id,xx.*,a.name
  73.     from xmldata a,
  74.     table( utl_excel.get_xls_table(blob_temp) ) xx
  75.     where a.name='MSOFFICE.EXCEL' and id=23 and sheet=4

  76. ex2:
  77. select * from table(utl_excel.get_xls_table(utl_lob.url2blob('ftp://172.17.2.43/pub/test001.xls')))
  78.     
  79. ************************************/

  80. -- p_sheet := -1 : select all sheet
  81. /* function get_xls_table(p_data in blob, p_sheet int default -1 ) RETURN xls_table2 PIPELINED ;
  82.   PRAGMA RESTRICT_REFERENCES(get_xls_table, WNDS, TRUST);*/
  83.   
  84.   function get_xls_table(p_data in blob, p_sheet int default -1 ) RETURN xls_table PIPELINED ;
  85. /*
  86.   PRAGMA RESTRICT_REFERENCES(xls_table, WNDS, TRUST);
  87. */


  88. END utl_excel;

  89.  
  90. /
  91. CREATE OR REPLACE PACKAGE body utl_excel AS
  92.   excel_parsing_error EXCEPTION;
  93.     pragma EXCEPTION_INIT(excel_parsing_error, -29532);

  94.   SUCCESS CONSTANT BINARY_INTEGER := 0;


  95. /**************** java implement ****************************/
  96.   FUNCTION newContext_java(data IN blob, error_code OUT ERROR_CODE_TYPE, error_message OUT error_message_type) RETURN ctxHandle
  97.   as LANGUAGE JAVA NAME
  98.    'corp.excel.ExcelReader.newcontext(oracle.sql.BLOB, int[], java.lang.String[]) return int';

  99.   PROCEDURE closeContext(ctx IN ctxHandle)
  100.   as LANGUAGE JAVA NAME
  101.    'corp.excel.ExcelReader.closecontext(int)';

  102.   function getSheets(ctx IN ctxHandle) return binary_integer
  103.   as LANGUAGE JAVA NAME
  104.    'corp.excel.ExcelReader.getSheets(int) return int';

  105.   function selectSheet(ctx IN ctxHandle, sheet binary_integer) return binary_integer
  106.   as LANGUAGE JAVA NAME
  107.    'corp.excel.ExcelReader.selectSheet(int, int) return int';
  108.    

  109.   function getRows(ctx IN ctxHandle) return binary_integer
  110.   as LANGUAGE JAVA NAME
  111.    'corp.excel.ExcelReader.getRows(int) return int';

  112.   function getColumns(ctx IN ctxHandle) return binary_integer
  113.   as LANGUAGE JAVA NAME
  114.    'corp.excel.ExcelReader.getColumns(int) return int';

  115.  -- for cell data length >4000 byte
  116.   procedure getClob(ctx IN ctxHandle, p_row in binary_integer, p_col in binary_integer, p_clob in out nocopy clob)
  117.   as LANGUAGE JAVA NAME
  118.    'corp.excel.ExcelReader.getClob(int, int, int, oracle.sql.CLOB[])';

  119. -- Oracle has a limit of 4000 bytes for a VARCHAR2, >4000 will by trim
  120.   FUNCTION getString(ctx IN ctxHandle, p_row in binary_integer, p_col in binary_integer) RETURN varchar2
  121.   as LANGUAGE JAVA NAME
  122.    'corp.excel.ExcelReader.getString(int, int, int) return java.lang.String';

  123.   function getSheetCount(ctx IN ctxHandle) return binary_integer
  124.   as LANGUAGE JAVA NAME
  125.    'corp.excel.ExcelReader.getSheetCount(int) return int';

  126. /*********************************************/
  127.  function number_to_date(v number) return date is
  128.  begin
  129.    --2個閏年 ?? --excel中Date返回的是number
  130.    return to_date('190001','YYYYMM') + v - 2 ;
  131.  end ;

  132.   PROCEDURE raise_error_if_failure(error_code ERROR_CODE_TYPE,
  133.                                     error_message ERROR_MESSAGE_TYPE)
  134.   IS
  135.   BEGIN
  136.     IF error_code <> SUCCESS THEN
  137.       raise_application_error(error_code, error_message);
  138.     END IF;
  139.   END;

  140.   FUNCTION newContext(data IN blob) RETURN ctxHandle
  141.   IS
  142.    error_code ERROR_CODE_TYPE;
  143.    error_message ERROR_MESSAGE_TYPE;
  144.    v_ctx ctxHandle;
  145.   BEGIN
  146.     v_ctx := newContext_java(data, error_code, error_message);
  147.     raise_error_if_failure(error_code, error_message);
  148.     return v_ctx;
  149.   end ;


  150.   function get_xls_val(data in blob) RETURN xls_data PIPELINED
  151.   is
  152.   ctx utl_excel.ctxHandle ;
  153.   r int ;
  154.   sheet_cnt pls_integer ;
  155.   row_cnt pls_integer;
  156.   col_cnt pls_integer;
  157.   cell cell_val ;
  158.   v_ret binary_integer;
  159.   begin
  160.     ctx := newcontext(data) ;
  161.     
  162.     sheet_cnt := getSheets(ctx) ;
  163.     for s in 0.. sheet_cnt-1 loop --多個excel sheet
  164.       cell.sheet := s;
  165.       v_ret := selectSheet(ctx, s) ;
  166.       
  167.       row_cnt := getrows(ctx) ;
  168.       col_cnt := getColumns(ctx) ;
  169.       for r in 0..row_cnt-1 loop --sheet中抓每一行
  170.         cell.row_idx :=r ;
  171.         for c in 0..col_cnt-1 loop --每行的每一列
  172.           cell.col_idx := c;
  173.           cell.data := getString(ctx, r, c) ;
  174.           pipe row (cell);
  175.         end loop;
  176.       end loop;
  177.     end loop;
  178.     closeContext(ctx) ;
  179.     return;
  180.     
  181.    exception
  182.       when NO_DATA_NEEDED then
  183.           utl_excel.closeContext(ctx) ;
  184.   end get_xls_val;




  185. procedure get_xls_row_val(p_row in out xls_row, ctx ctxHandle, row_idx pls_integer, maxcol pls_integer) is
  186.   v_cellval celltype ;
  187.   procedure fill_cell(v_cellval celltype, c pls_integer) is
  188.   begin
  189.     case
  190.       when c=0 then p_row.col_a := v_cellval ;
  191.       when c=1 then p_row.col_b := v_cellval ;
  192.       when c=2 then p_row.col_c := v_cellval ;
  193.       when c=3 then p_row.col_d := v_cellval ;
  194.       when c=4 then p_row.col_e := v_cellval ;
  195.       when c=5 then p_row.col_f := v_cellval ;
  196.       when c=6 then p_row.col_g := v_cellval ;
  197.       when c=7 then p_row.col_h := v_cellval ;
  198.       when c=8 then p_row.col_i := v_cellval ;
  199.       when c=9 then p_row.col_j := v_cellval ;
  200.       when c=10 then p_row.col_k := v_cellval ;
  201.       when c=11 then p_row.col_l := v_cellval ;
  202.       when c=12 then p_row.col_m := v_cellval ;
  203.       when c=13 then p_row.col_n := v_cellval ;
  204.       when c=14 then p_row.col_o := v_cellval ;
  205.       when c=15 then p_row.col_p := v_cellval ;
  206.       when c=16 then p_row.col_q := v_cellval ;
  207.       when c=17 then p_row.col_r := v_cellval ;
  208.       when c=18 then p_row.col_s := v_cellval ;
  209.       when c=19 then p_row.col_t := v_cellval ;
  210.     end case;
  211.   end;
  212. begin
  213.   for c in 0..maxcol-1 loop
  214.     v_cellval := getString(ctx, row_idx, c) ;
  215.     fill_cell(v_cellval, c) ;
  216.   end loop;
  217. end ;

  218. function get_xls_table(p_data in blob, p_sheet int) RETURN xls_table PIPELINED
  219. is
  220. ctx utl_excel.ctxHandle ;
  221. r int ;
  222. row_cnt pls_integer;
  223. col_cnt pls_integer;
  224. sheet_cnt pls_integer ;
  225. vrow xls_row ;
  226. v_ret binary_integer;
  227. begin
  228.   
  229.   ctx := utl_excel.newcontext(p_data) ;
  230.   sheet_cnt := getSheets(ctx) ;
  231.   
  232.   <<loop_sheet>>
  233.   for s in 0.. sheet_cnt-1 loop --多個excel sheet
  234.     
  235.     if (p_sheet = -1 or p_sheet = s) then
  236.     
  237.       vrow := null; -- 需先清空數據,可能不同sheet資料列不一樣多
  238.       vrow.sheet := s + 1 ;
  239.       
  240.       v_ret := selectSheet(ctx, s) ;
  241.       row_cnt := getrows(ctx) ;
  242.       col_cnt := getColumns(ctx) ;
  243.       
  244.       if col_cnt >c_max_cols then
  245.         col_cnt := c_max_cols ;
  246.       end if ;
  247.       
  248.       <<loop_rows>>
  249.       for r in 0..row_cnt-1 loop -- 抓每一行數據
  250.         vrow.row_idx := r + 1;
  251.         get_xls_row_val(vrow, ctx, r, col_cnt ) ;
  252.         pipe row (vrow);
  253.       end loop loop_rows;
  254.     end if ;
  255.     
  256.   end loop loop_sheet;

  257.   utl_excel.closeContext(ctx) ;
  258.   
  259.   exception
  260.     when NO_DATA_NEEDED then
  261.         utl_excel.closeContext(ctx) ;
  262.     when excel_parsing_error then
  263.         utl_excel.closeContext(ctx) ;
  264.         raise_application_error(-20013, 'open excel error'||sqlerrm);
  265. end get_xls_table;



  266. END utl_excel;
  267. /

java 代碼 Excelobj.java


点击(此处)折叠或打开

  1. create or replace and compile java source named "corp/excel/ExcelReader" as
  2. package corp.excel;
  3. import oracle.CartridgeServices.ContextManager;
  4. import java.util.Date;
  5. import jxl.Workbook;
  6. import jxl.Sheet;
  7. import jxl.Cell;
  8. import jxl.NumberCell;
  9. import jxl.DateCell;
  10. import jxl.CellType;
  11. import java.io.IOException ;
  12. import java.io.Writer;
  13. import java.io.StringWriter;
  14. import java.io.PrintWriter;
  15. import java.sql.SQLException;
  16. import oracle.CartridgeServices.CountException ;
  17. import jxl.read.biff.BiffException ;
  18. import oracle.CartridgeServices.InvalidKeyException ;
  19. import java.text.SimpleDateFormat;
  20. import java.text.DateFormat;
  21. import java.util.Calendar;
  22. import java.math.BigDecimal;
  23. import java.util.HashSet;

  24. /**************
  25. 2014-04-01 重新封裝jxl.Workbook

  26.  int[] errorCode, errorCode=0 沒有錯誤,
  27.  String[] errorMessage 錯誤信息
  28. ***************/

  29. public class ExcelReaderObj
  30. {
  31.    public jxl.Workbook xls =null;
  32.    public jxl.Sheet active_sheet =null;
  33. }



  34. public class ExcelReader
  35. {
  36.   public static final int SUCCESS = 0;
  37.   public static final int FAILURE = -20013;
  38.   
  39.   public static final String[] DateFormat = new String[] {
  40.          "yyyy/mm/dd",
  41.          "YYYYMMDD",
  42.          "M\\月D\\日",
  43.          "YYYY/M/D",
  44.          "m\"月\"d\"日\""
  45.          };

  46.   public static HashSet xlsDateFormat = new HashSet();
  47.   
  48.   private static boolean contains(String[] array, String key)
  49.   {
  50.     java.util.Arrays.sort(array);
  51.     return java.util.Arrays.binarySearch(array, key) >= 0;
  52.   }
  53.   
  54.   private static int SQLfailure(SQLException e, int[] errorCode, String[] errorMessage)
  55.   {
  56.       errorCode[0] = e.getErrorCode();
  57.       errorMessage[0] = e.getMessage();
  58.       return FAILURE;
  59.   }

  60.   private static String ExceptionString(Exception e)
  61.   {
  62.       Writer writer = new StringWriter();
  63.       PrintWriter printWriter = new PrintWriter(writer);
  64.       e.printStackTrace(printWriter);
  65.       return writer.toString();
  66.   }
  67.       
  68.   private static int Failure(Exception e, int[] errorCode, String[] errorMessage)
  69.   {
  70.       errorCode[0] = -20013 ;
  71.       errorMessage[0] = ExceptionString(e) ;
  72.       return FAILURE;
  73.   }
  74.   
  75.   public static int newcontext(java.io.InputStream data, int[] errorCode, String[] errorMessage)
  76.   {
  77.     errorCode[0] = SUCCESS ;
  78.     
  79.     for (int i=0; i< DateFormat.length; i++) {
  80.        xlsDateFormat.add(DateFormat[i]);
  81.     }
  82.     
  83.     try {
  84.         ExcelReaderObj xlsobj = new ExcelReaderObj();
  85.         xlsobj.xls = Workbook.getWorkbook( data ) ;
  86.         return ContextManager.setContext(xlsobj) ;
  87.     } catch (Exception e) {
  88.       return Failure(e, errorCode, errorMessage);
  89.     }
  90.   }
  91.   

  92.   public static int newcontext(oracle.sql.BLOB data, int[] errorCode, String[] errorMessage)
  93.   {
  94.     try {
  95.        return newcontext( data.getBinaryStream(), errorCode, errorMessage);
  96.     } catch (SQLException e) {
  97.       return SQLfailure(e, errorCode, errorMessage);
  98.     }
  99.   }

  100.   public static int newcontext(oracle.sql.BFILE data, int[] errorCode, String[] errorMessage)
  101.   {
  102.     try {
  103.         return newcontext( data.getBinaryStream(), errorCode, errorMessage);
  104.     } catch (SQLException e) {
  105.       return SQLfailure(e, errorCode, errorMessage);
  106.     }
  107.   }

  108.   public static int closecontext(int ctx)
  109.   throws SQLException, CountException, InvalidKeyException
  110.   {
  111.     ExcelReaderObj xlsobj = (ExcelReaderObj) ContextManager.clearContext(ctx) ;
  112.     xlsobj.xls.close() ;
  113.     xlsobj = null;
  114.     return ContextManager.count ;
  115.   }
  116.   

  117.   public static int getProper(int ctx, String key, int[] v_int, String[] v_String)
  118.   throws SQLException, CountException, InvalidKeyException
  119.   {
  120.     ExcelReaderObj xlsobj = (ExcelReaderObj) ContextManager.getContext(ctx) ;
  121.     
  122.     v_int[0] = 0;
  123.     v_String[0] = "";
  124.     
  125.     if (key.equals("Sheets"))
  126.     {
  127.       v_int[0] = xlsobj.xls.getNumberOfSheets();
  128.     }
  129.     else if (key.equals("rowCount"))
  130.     {
  131.       v_int[0] = xlsobj.active_sheet.getRows();
  132.     }
  133.     else if (key.equals("columnsCount"))
  134.     {
  135.       v_int[0] = xlsobj.active_sheet.getColumns();
  136.     }
  137.     else if (key.equals("sheetName"))
  138.     {
  139.       v_String[0] = xlsobj.active_sheet.getName();
  140.     }
  141.     
  142.     
  143.     return 0;
  144.   }

  145.   public static int getSheets(int ctx )
  146.   throws SQLException, CountException, InvalidKeyException
  147.   {
  148.     ExcelReaderObj xlsobj = (ExcelReaderObj) ContextManager.getContext(ctx) ;
  149.     return xlsobj.xls.getNumberOfSheets();
  150.   }

  151.  public static int selectSheet(int ctx, int sheet)
  152.   throws SQLException, CountException, InvalidKeyException
  153.   {
  154.     ExcelReaderObj xlsobj = (ExcelReaderObj)ContextManager.getContext(ctx) ;
  155.     xlsobj.active_sheet = xlsobj.xls.getSheet(sheet);
  156.     return 0 ;
  157.   }

  158.  public static int getRows(int ctx)
  159.   throws SQLException, CountException, InvalidKeyException
  160.   {
  161.     ExcelReaderObj xlsobj = (ExcelReaderObj)ContextManager.getContext(ctx) ;
  162.     return xlsobj.active_sheet.getRows();
  163.   }

  164.  public static int getColumns(int ctx)
  165.   throws SQLException, CountException, InvalidKeyException
  166.   {
  167.     ExcelReaderObj xlsobj = (ExcelReaderObj)ContextManager.getContext(ctx) ;
  168.     return xlsobj.active_sheet.getColumns() ;
  169.   }


  170.   public static void getClob(int ctx, int row, int col, oracle.sql.CLOB[] outval)
  171.   throws SQLException, CountException, InvalidKeyException
  172.   {
  173.     ExcelReaderObj xlsobj = (ExcelReaderObj)ContextManager.getContext(ctx) ;
  174.     Cell vcell = xlsobj.active_sheet.getCell(col,row) ;
  175.     outval[0].setString(1, vcell.getContents()) ;
  176.   }
  177.   


  178.   
  179.   
  180.     private static String dayAddition(int num, String vformat)
  181.     {
  182.       try {
  183. // vformat = "yyyy-MM-dd"
  184.           SimpleDateFormat timeformat = new SimpleDateFormat(vformat);
  185.           java.util.Date date = timeformat.parse("1900-1-1");
  186.           Calendar a = Calendar.getInstance();
  187.           a.setTime(date);
  188.           a.add(Calendar.DATE, (num-2)); //為什麼要 (num-2) ?
  189.           return timeformat.format(a.getTime());
  190.         } catch (java.text.ParseException e)
  191.         {
  192.           return "Parse Date Error";
  193.         }
  194.     }
  195.     
  196.     private static String getOracleString(String str)
  197.     {
  198.         if (str.length()<1200) { //不會超過4000 byte
  199.            return str ;
  200.         }
  201.         
  202.         int len = ( str.length() > 4000 ) ? 4000 : str.length();
  203.         
  204.         byte v_bytes[] = str.substring(0, len).getBytes() ;
  205.         if (v_bytes.length <= 4000) {
  206.             return str;
  207.         } else
  208.         {
  209. // byte[] buf = new byte[4000];
  210. // System.arraycopy(v_bytes, 0, buf, 0, 4000);
  211.             return new String(v_bytes, 0, 4000) ;
  212.         }
  213.     }

  214.     private static String getDoubleString(double var1)
  215.     {
  216.        String s = Double.toString(var1) ;

  217.        if(s.substring(s.length()-2).equals(".0")) //截斷 .0
  218.        {
  219.            return s.substring(0, s.length()-2);
  220.        }else{
  221.            return s;
  222.        }
  223.     }
  224.     
  225.     private static String getFormat(Cell cell)
  226.     {
  227.        jxl.format.CellFormat vcf = cell.getCellFormat() ;
  228.        try {
  229.          if (vcf != null) {
  230.             return vcf.getFormat().getFormatString();
  231.          }
  232.        } catch (java.lang.NullPointerException e) {
  233.        }
  234.        return "";
  235.     }
  236.     
  237.   
  238.   
  239. /*****************************************
  240.     Oracle has a limit of 4000 bytes for VARCHAR2
  241. ******************************************/
  242.   public static String getString(int ctx, int row, int col)
  243.   throws CountException, InvalidKeyException
  244.   {
  245.     ExcelReaderObj xlsobj = (ExcelReaderObj)ContextManager.getContext(ctx) ;
  246.     
  247.     Cell cell = xlsobj.active_sheet.getCell(col,row) ;
  248.     CellType ctype = cell.getType();
  249.     String vformat = getFormat(cell);
  250.      
  251.     if ( ctype == CellType.LABEL )
  252.     {
  253.         return getOracleString(cell.getContents()) ;
  254.     }
  255.     else if (ctype == CellType.NUMBER || ctype == CellType.NUMBER_FORMULA)
  256.     { //直接getContents, number型會丟失精度

  257.        NumberCell nc = (NumberCell)cell;
  258. /*****
  259.  excel內部存放的是 serial number 型的日期,從1900到現在天數
  260. ****/
  261. // contains(xlsDateFormat, vformat)
  262.        if ((ctype == CellType.NUMBER) && (xlsDateFormat.contains(vformat)))
  263.        {
  264.           return dayAddition((int)nc.getValue(), vformat);
  265.        }

  266. // return getDoubleString(nc.getValue());
  267.        return cell.getContents();
  268.     }
  269.     else if (ctype == CellType.DATE || ctype == CellType.DATE_FORMULA )
  270.     {
  271. // vformat = "yyyy-mm-dd" ;
  272.         DateFormat format1 = new SimpleDateFormat("yyyy/MM/dd");
  273.         return format1.format( ((DateCell)cell).getDate() );
  274.     }
  275.     else
  276.     {
  277.         return getOracleString(cell.getContents()) ;
  278.     }
  279.   }
  280.   

  281.   public static int getcnt(int ctx)
  282.   throws SQLException, CountException, InvalidKeyException
  283.   {
  284.     return ContextManager.count ;
  285.   }



  286. // ???need fix
  287.   public void getValue(int ctx, int row, int col,
  288.   int[] datatype,
  289.   String[] v_String,
  290.   Date[] v_Date
  291.   )
  292.   throws SQLException, CountException, InvalidKeyException
  293.   {
  294.     ExcelReaderObj xlsobj = (ExcelReaderObj)ContextManager.getContext(ctx) ;
  295.     
  296.     Cell cell = xlsobj.active_sheet.getCell(col,row) ;
  297.     //直接getContents, number型會丟失精度
  298.     if(cell.getType()==CellType.NUMBER ||cell.getType()==CellType.NUMBER_FORMULA)
  299.     {
  300.        NumberCell nc=(NumberCell)cell;
  301.        String s=Double.toString(nc.getValue()) ;
  302.        v_String[0] = s ;
  303.        
  304.     } else
  305.     {
  306.         v_String[0] = getOracleString(cell.getContents()) ;
  307.     }

  308.   }


  309.   private static String NumberToDate(long s)
  310.   {
  311.          String rtn= "1900-01-01";
  312.          try{
  313.           SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd");
  314.           java.util.Date date1 = new java.util.Date();
  315.           date1 = format.parse("1900-01-01");
  316.           long i1 = date1.getTime();

  317. /****************
  318.   ?里要?去2,(s-2) 不然日期?提前2天,具体原因不清楚,
  319.   估?和java??是?1970-01-01?始有?
  320.   而excel里面的?算是?1900-01-01?始
  321. ***********/
  322.           i1= i1/1000+( (s-2)*24*3600);
  323.           date1.setTime(i1*1000);
  324.           rtn=format.format(date1);
  325.          }catch(Exception e){
  326.           rtn= "1900-01-01";
  327.          }
  328.          return rtn;
  329.          
  330.   }

  331. }




注意事项:
  1. oracle 10g的jdk是1.4
  jxl版本不能用最新的.  我用的是jxl-2.6.jar

2.  装入jar请用 loadjava
  loadjava -u user/pass  -v -f jxl-2.6.jar

3. pb装入excel到blob请用updateblob

4. Excel 2007可以用as_xlsx_read读取,我的思路参考as_xlsx_read后些出来的
  http://technology.amis.nl/2013/01/19/read-a-excel-xlsx-with-plsql/
  select * from table( as_read_xlsx.read( as_read_xlsx.file2blob( 'DOC', 'Book1.xlsx' ) ) );


欢迎和大家一起交流oracle技术.

2014/02/24修改
當長度>4000時截斷
                                                   阿飞
                                              2014/02/21

阅读(2935) | 评论(0) | 转发(1) |
给主人留下些什么吧!~~