急求:oracle存储过程???

yuanhangq220 2013-11-19 09:43:00
oracle入门级,想写个存储过程供pro*c调用,将byte型数据存入blob型字段表中,byte型数据通过varchar2传入。下面自己写的,调用后表中出现很多0x3F,应该是cast_to_raw导致的,怎么解决?是否还有其他问题???
procedure write(i_lob_loc in out nocopy BLOB, i_data in VARCHAR2) as
p_buffer raw(2048);
p_size number := lengthb(i_data);
p_offset number := 0;
p_tmp varchar(2048);
begin
if p_size > 0 then
if p_size <= 2048 then
p_buffer := utl_raw.cast_to_raw(i_data);
dbms_lob.write(i_lob_loc, p_size, 1, p_buffer);
else
p_tmp := substr(i_data, 0, 2048);
p_buffer := utl_raw.cast_to_raw(p_tmp);
dbms_lob.write(i_lob_loc, 2048, 1, p_buffer);
p_size := p_size - 2048;
p_offset := p_offset + 2048;
while p_size > 0 loop
begin
if p_size <= 2048 then
p_tmp := substr(i_data, p_offset, p_size);
p_buffer := utl_raw.cast_to_raw(p_tmp);
dbms_lob.writeappend(i_lob_loc, p_size, p_buffer);
p_size := 0;
else
p_tmp := substr(i_data, p_offset, 2048);
p_buffer := utl_raw.cast_to_raw(p_tmp);
dbms_lob.writeappend(i_lob_loc, 2048, p_buffer);
p_size := p_size - 2048;
end if;
end;
end loop;
end if;
end if;
end;
...全文
274 16 打赏 收藏 转发到动态 举报
写回复
用AI写文章
16 条回复
切换为时间正序
请发表友善的回复…
发表回复
yuanhangq220 2013-11-20
  • 打赏
  • 举报
回复
buffer很小的情况也测过。这种情况是少见,从网上找了很久没答案才到这里发帖。现在还没结果,如有答案当然会分享。
CT_LXL 2013-11-20
  • 打赏
  • 举报
回复
引用 15 楼 yuanhangq220 的回复:
非常感谢zlloct的回答,问题解决了。 proc中调用存储过程写byte数据时,传入参数使用raw型就可以了。 proc中: unsigned char buffer[BUFFER_SIZE]; EXEC SQL VAR bufferIS RAW(BUFFER_SIZE);///必须的,可以将buffer当做raw型使用了 procedure中直接调用dbms_lob.write就可以了。
谢谢分享
yuanhangq220 2013-11-20
  • 打赏
  • 举报
回复
非常感谢zlloct的回答,问题解决了。 proc中调用存储过程写byte数据时,传入参数使用raw型就可以了。 proc中: unsigned char buffer[BUFFER_SIZE]; EXEC SQL VAR bufferIS RAW(BUFFER_SIZE);///必须的,可以将buffer当做raw型使用了 procedure中直接调用dbms_lob.write就可以了。
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
byte型随机数我都没用过,在oracle中也没有碰到过,我不知道你能不能先让这种数据的长度小一点,这样能够排除由于buffer引起的错误,这个问题太少见了,lz如果知道答案了分享一下吧
yuanhangq220 2013-11-19
  • 打赏
  • 举报
回复
如果我的varchar2中存放的是可见字符,你的example是ok的,但我存放的是byte型随机数,调用UTL_RAW.cast_to_raw转换的时候就出问题了。
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
找到EXAMPLE, --创建测试表 CREATE Table T_BLOB (ID NUMBER, BLB Blob); --编写PLSQL declare v_blob BLOB; amount BINARY_INTEGER; offset INTEGER; v_char VARCHAR2(1000); Begin --往BLOB类型的字段插入记录,不能直接填入值,必须先往BLOB字段插入一个EMPTY_BLOB() INSERT INTO T_BLOB VALUES(1,EMPTY_BLOB()); COMMIT; --更新和新增一样要将BLOB字段设置为EMPTY_BLOB() update T_BLOB set blb = empty_blob() where id = 1; select blb into v_blob from T_BLOB where id = 1 for update; DBMS_LOB.OPEN(v_blob,DBMS_LOB.LOB_READWRITE); v_char := 'This is an sample!sadfsa'; amount := LENGTHB(v_char); offset := 1; --UTL_RAW.cast_to_raw函数将字符串转换成二进制数 DBMS_LOB.WRITE(v_blob,amount,offset,UTL_RAW.cast_to_raw(v_char)); DBMS_LOB.CLOSE(v_blob); commit; end;
yuanhangq220 2013-11-19
  • 打赏
  • 举报
回复
谢谢,varchar2作为变量可以有32k
yuanhangq220 2013-11-19
  • 打赏
  • 举报
回复
又看了一下oracle的文档如下,现在的问题就是,如何将byte数据不做任何改变的放到raw型变量中; 或者另一解决方案:将我的存储过程输入参数改为blob型,但问题是在pro*c中如何将blob locator变量指向我的byte数据???? ------------------------------------------------------------------------------ http://docs.oracle.com/cd/B28359_01/appdev.111/b28419/d_lob.htm#i999593 WRITE Procedures This procedure writes a specified amount of data into an internal LOB, starting from an absolute offset from the beginning of the LOB. The data is written from the buffer parameter. WRITE replaces (overwrites) any data that already exists in the LOB at the offset, for the length you specify. Syntax DBMS_LOB.WRITE ( lob_loc IN OUT NOCOPY BLOB, amount IN INTEGER, offset IN INTEGER, buffer IN RAW); DBMS_LOB.WRITE ( lob_loc IN OUT NOCOPY CLOB CHARACTER SET ANY_CS, amount IN INTEGER, offset IN INTEGER, buffer IN VARCHAR2 CHARACTER SET lob_loc%CHARSET);
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
OH ~~~我都只用过针对varchar2这种类型的
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
还有一点需要注意的是ORACLE 中varchar 的最大长度好像是4000
yuanhangq220 2013-11-19
  • 打赏
  • 举报
回复
dbms_lob.write传入参数有两种:varchar2是针对clob的,blob的传入参数是raw吧
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
但是dbms_lob.write传入的参数直接为VARCHAR2,不能为RAW 啊
yuanhangq220 2013-11-19
  • 打赏
  • 举报
回复
sorry,没写完不小心提交了,接上---- 直接用dbms_lob.write(i_lob_loc, p_size, 1, i_data);的话会报错: ORA-06502: PL/SQL: numeric or value error: hex to raw conversion error 我在pro c中是这么处理的: unsigned char data[16384] = {..........};///byte随机数 varchar i_data[16384]; memcpy(i_data.arr, data, 16384); i_data.len = 16384;
yuanhangq220 2013-11-19
  • 打赏
  • 举报
回复
谢谢回复 直接用dbms_lob.write(i_lob_loc, p_size, 1, i_data);的话会报错:
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
dbms_lob.write(i_lob_loc, p_size, 1, p_buffer); -> dbms_lob.write(i_lob_loc, p_size, 1, i_data);
CT_LXL 2013-11-19
  • 打赏
  • 举报
回复
p_buffer := utl_raw.cast_to_raw(i_data); dbms_lob.write(i_lob_loc, p_size, 1, p_buffer); 你这里为什么要传RAW 进去啊,这样的TYPE传进去应该不行吧,直接传i_data啊不需要转换成RAW,你可以试试,我能够成功,如果传RAW会报错

17,086

社区成员

发帖
与我相关
我的任务
社区描述
Oracle开发相关技术讨论
社区管理员
  • 开发
  • Lucifer三思而后行
  • 卖水果的net
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧