2、Matlab调用Oracl带游标参数输出的存储过程

笔者也是将工作之中遇到的问题进行了搜集与整理,才完成该文的编写,希望能帮助到有需要的朋友。

2.1、PLSQL中的存储过程

 PROCEDURE p_test_for_matlab(p_i IN VARCHAR2, p_cur OUT type_cur) IS
BEGIN
OPEN p_cur FOR
SELECT * FROM mes_imp_operate_log d WHERE rownum <= p_i;
END;

下面执行存储过程返回(官网文档给的,处理返回游标时,很明显这样不行,满足不了需求):

% Execute query and get data from Oracle
curs = runstoredprocedure(conn, 'mes_wytest_pkg.p_test_for_matlab', {}, {oracle.jdbc.OracleTypes.CURSOR});

论坛Matlab团队的人给出解释是(因为runstoredprocedure该函数中包含了一句关闭游标的动作。因此无法获取和游标相关的数据,意思就是对于返回游标的存储过程,不好使)。 但是,上诉runstoredprocedure 可以执行返回值不是游标的存储过程。)

----------------------------------------------推荐使用的---------------------------------------------------------------------------
2.2、官网论坛,给出的写法是(附带runCursorSP.m):
conn = database('AE','e','e', 'oracle.jdbc.driver.OracleDriver','jdbc:oracle:thin:@10.24.10.3:1521:');
curs = runCursorSP(conn, 'mes_wytest_pkg.p_test_for_matlab', {}, {oracle.jdbc.OracleTypes.CURSOR});
a = curs{,};
close(conn);

返回的结果是:

这就是我们要的东西。

-------------------------------------------------------拓展修改应用----------------------------------------------------------------

2.3、我们修改试试,尝试将存储过程修改成返回Number类型

curs = runCursorSP(conn, 'mes_wytest_pkg.p_test_for_matlab', {}, {oracle.jdbc.OracleTypes.NUMBER});
PROCEDURE p_test_for_matlab(p_i IN VARCHAR2, p_cur OUT NUMBER) IS
BEGIN
SELECT COUNT(*)
INTO p_cur
FROM mes_imp_operate_log d
WHERE rownum <= p_i;
END;

测试结果显示:

此处也可以使用 runstoredprocedure。

其 runCursorSP.m 文件是这样定义的(直接复制就好):

function x = runCursorSP(c,spcall,inarg,typeout)
%RUNCURSORSP Function to run an Oracle stored procedure that returns a
%cursor object. Usage is same as RUNSTOREDPROCEDURE %Set defaults for inarg and typeout
if nargin <
inarg = [];
end
if nargin <
typeout = [];
end %Get JDBC connection Handle
h = c.Handle; %Get Database name
dMetaData = dmd(c);
sDbName = get(dMetaData,'DatabaseProductName'); %Build stored procedure call
spcall = [spcall '('];
for i = :length(inarg)
if isnumeric(inarg{i}) || islogical(inarg{i})
inarg{i} = num2str(inarg{i},);
elseif strcmp(sDbName,'MySQL') || strcmp(sDbName,'Microsoft SQL Server')
inarg{i} = ['''' inarg{i} ''''];
end
spcall = [spcall inarg{i} ',']; %#ok, not sure how long spcall will be
end
numout = length(typeout);
for i = :numout
spcall = [spcall '?,']; %#ok, not sure how long spcall will be
end %Allow for procedures with no inputs or outputs
if ~(isempty(inarg) && isempty(typeout))
spcall(end) = ')';
else
spcall(end) = [];
end
spcall = ['{call ' spcall '}']; %Create callable statement
csmt = h.prepareCall(spcall); %Register output parameters
for i = :numout
csmt.registerOutParameter(i,typeout{i});
end %Execute callable statement, method depends on output parameters
if ~isempty(typeout)
csmt.executeUpdate;
else
try
x = csmt.execute;
catch exception
error(message('database:runstoredprocedure:returnedResultSet', exception.message));
end
return
end %Return output parameters as native data types
x = cell(numout,);
for i = :numout
x{i} = csmt.getObject(i); %Check if Oracle resultset returned if(isa(x{i}, 'oracle.jdbc.driver.OracleResultSetImpl'))
data = fetchCursorData(c, x{i});
x{i} = data;
end end %Close callable statement
close(csmt)
end
function data = fetchCursorData(conn, rs)
%FETCHCURSORDATA function to fetch data in a resultset object returned when
% calling a stored procedure that returns a cursor.
% data = fetchCursorData(conn, rs)
% conn : Database Connection Object
% rs : ResultSet object %Fetch the data h = conn.Handle; fet = com.mathworks.toolbox.database.fetchTheData(h, rs, ''); md = getTheMetaData(fet);
status = validResultSet(fet,md); if(status ~= ) %Get preferences
p = setdbprefs({'NullStringRead';'NullNumberRead';'DataReturnFormat'});
tmpNullNumberRead = 'NullNumberReadPlaceHolderCFG3358'; %Fetch batchCount rows
resultSetMetaData = getValidResultSet(fet,md);
dataFetched = dataFetch(fet,resultSetMetaData,p.NullStringRead,tmpNullNumberRead); %Convert java.util.vector to cell array
%Get number of rows and columns rsmd = getMetaData(rs);
ncols = getColumnCount(rsmd); nrows = size(dataFetched) / ncols;
data = system_dependent(,dataFetched,nrows)'; %Convert NullNumberRead value into numeric value
i = find(strcmp(data,tmpNullNumberRead));
data(i) = {str2num(p.NullNumberRead)}; else
error('No valid resultset');
end %close resultset
rs.close; end

谢谢阅读!

分享是美德!

分享共进步!

Matlab调用返回游标的存储过程的分析和处理的更多相关文章

  1. Oracle 存储过程调用返回游标的另一个存储过程。

    一个扩展存储过程调用另一个存储过程,示例: 被调用存储过程:最后会返回一个游标,游标返回一个值.调用这个存储过程的存储过程同样需要获取它. procedure SearchBill --根据到货单号查 ...

  2. (转载)oracle 在一个存储过程中调用另一个返回游标的存储过程

    原文链接:http://www.jb51.net/article/20160.htm 实际项目当中经常需要在一个存储过程中调用另一个存储过程返回的游标,本文列举了两种情况讲述具体的操作方法. 第一种情 ...

  3. sqlserver 存储过程返回游标的处理

    创建表: create table tb1( id int , name ) ) ------------------------------------------------- 创建返回游标的存储 ...

  4. mybatis 调用存储过程 返回游标 实例

    存储过程示例: create or replace procedure Fsp_Plan_CheckPrj(v_grantno varchar2, v_deptcode number, v_curso ...

  5. ibatis调存储过程返回游标

    http://blog.sina.com.cn/s/blog_6f3ca78f01010pmj.html iBatic调用与JAVA调用很类似,只是JAVA把参数的注册放到了类里面,而iBatis把参 ...

  6. C#调用SQL中的存储过程中有output参数,存储过程执行过程中返回信息

      C#调用SQL中的存储过程中有output参数,类型是字符型的时候一定要指定参数的长度.不然获取到的结果总是只有第一字符.本人就是由于这个原因,折腾了很久.在此记录一下,供大家以后参考! 例如: ...

  7. java Servlet+mysql 调用带有输入参数和返回值的存储过程(原创)

    这个数据访问的功能,我在.NET+Mysql .NET+Sqlserver  PHP+Mysql上都实现过,并且都发布在了我博客园里面,因为我觉得这个功能实在是太重要,会让你少写很多SQL语句不说,还 ...

  8. JDBC和JPA调用储存过程 接收存储过程有返回值

    ============jdbc==========================================--java代码:一个输出参数--String connURL = null;Con ...

  9. oracle ibatis 存储过程 返回游标 嵌套表

    自己解决问题了 问题总结: 1.index by表不能存储在数据库中的type中,故选择嵌套表. 2.ibatis不支持oracle的复合数据类型的返回.(个人理解) 3.替代方案:用返回oracle ...

随机推荐

  1. 开篇-QT完全手册

    嵌入式工具Qt的安装与使用 摘要 Qt是Trolltech公司的一个产品.Trolltech是挪威的一家软件公司,主要开 发两种产品:一种是跨平台应用程序界面框架:另外一种就是提供给做嵌入式Linux ...

  2. C/C++嵌入式开发面试题

    C/C++嵌入式开发面试题 预处理器(Preprocessor) 1. 用预处理指令#define 声明一个常数,用以表明1年中有多少秒(忽略闰年问题) #define SECONDS_PER_YEA ...

  3. iOS:UITableViewCell自定义单元格

    UITableViewCell:自定义的单元格,可以在xib中创建单元格,也可以在storyBorad中创建单元格.有四种创建方式 <1>在storyBorad中创建的单元格,它是静态的单 ...

  4. HashTable HashMap HashSet区别(java)

    Hashtable: 1. key和value都不许有null值 2. 使用enumeration遍历 3. 同步的,每次只有一个线程能够访问 4. 在java中Hashtable是H大写,t小写,而 ...

  5. Template Method 模板方法 MD

    Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱 MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina ...

  6. jqGrid常用属性和方法介绍

    jqGrid API中文手册:http://blog.mn886.net/jqGrid/ 一.jqGrid属性: width:Grid的宽度,如果未设置,则宽度应为所有列宽的之和:如果设置了宽度,则每 ...

  7. Jmeter-Maven-Plugin高级应用:Proxy Configuration

    Proxy Configuration Pages 12 Home Adding additional libraries to the classpath Advanced Configuratio ...

  8. 隐马尔可夫模型HMM与维特比Veterbi算法(二)

    隐马尔可夫模型HMM与维特比Veterbi算法(二) 主要内容: 前向算法(Forward Algorithm) 穷举搜索( Exhaustive search for solution) 使用递归降 ...

  9. 【Javascript Demo】根据Email地址跳转到相应的邮箱登录页面

    我的初步想法是通过指定的邮箱地址自动查找到对应的邮箱登录页面,但是用数据库.js什么的都有局限性,因为各种各样的邮箱太多了,不能都包含的到,网上找了半天都没有找到满意的答案,自己又想不出方法,只能暂时 ...

  10. android触控,先了解MotionEvent

    MotionEvent源代码可以在ocs看到,当然你也可以在SDK中下载源代码,或者其他地方,如: https://github.com/CyanogenMod/android_frameworks_ ...